iT邦幫忙

2018 iT 邦幫忙鐵人賽
DAY 26
0
自我挑戰組

花式PHP系列 第 27

PHP SPL:SplFixedArray

它是什麼?

SplFixedArray 就是固定長度的陣列。
底下是 php 的 SplFixedArray 跟 array 的比較:

功能 SplFixedArray array
foreach O O
string key X O
動態長度 X O
各種內建函式支援 X O
ArrayIterator X O

看起來好像不太能打

這樣看起來,好像沒有什麼用 SplFixedArray 的理由對吧 XD
但其實 SplFixedArray 最大的好處是:

  • 因為它只使用整數當 key,所以記憶體佔用更小、效能更高
  • 根據 artaxerxes 的說法,SplFixedArray 的效能完封 array

用法

創造一個 SplFixedArray

<?php

// new SplFixedArray 時需要手動指定陣列長度
$fixedArray = new SplFixedArray(1000);

<?php

$array = range(1, 10);

$fixedArray = SplFixedArray::fromArray($array);

使用 SplFixedArray

SplFixedArray 提供一些 array 也有的基礎語法:

  • foreach
  • count()
  • $fixedArray[$key] 這種語法

但它不能:

  • 使用許多 array 可用的內建函式(排序等等)
  • $fixedArray[] = $value 這種語法,因為SplFixedArray的長度是固定的

效能測試

使用 array

<?php

$start = microtime(TRUE);

$array = [];

/**
 * 底下一模一樣
 */
 
for ($i = 0; $i < 500000; $i++) {
    $array[$i] = $i;
}

echo (microtime(TRUE) - $start) . PHP_EOL;
$start = microtime(TRUE);

foreach ($array as $key => $value) {
    //
}

echo (microtime(TRUE) - $start) . PHP_EOL;
echo memory_get_peak_usage(TRUE);

使用 SplFixedArray

<?php

$start = microtime(TRUE);

$array = new SplFixedArray(500000);

/**
 * 底下一模一樣
 */
 
for ($i = 0; $i < 500000; $i++) {
    $array[$i] = $i;
}

echo (microtime(TRUE) - $start) . PHP_EOL;
$start = microtime(TRUE);

foreach ($array as $key => $value) {
    //
}

echo (microtime(TRUE) - $start) . PHP_EOL;
echo memory_get_peak_usage(TRUE);

PHP 5.6.29 測試結果

測試 SplFixedArray array
寫入 0.05386 0.23111
讀取 0.03572 0.02204
記憶體佔用 28573696 72876032

PHP 7.1.0 測試結果

測試 SplFixedArray array
寫入 0.01405 0.03015
讀取 0.01503 0.00756
記憶體佔用 10100736 18878464

結論

看起來 SplFixedArray 並沒有完封 array。

儘管寫入速度及記憶體佔用 SplFixedArray 的巨大優勢都是毋庸置疑的,
但讀取速度在兩個版本都沒有比較快。

所以讓 SplFixedArray 大展身手的場景,
肯定不會是單純為了增進效能而改用 SplFixedArray,
應該更偏向出現「佔用過多記憶體」時需要做優化的場景。

收工~


上一篇
PHP SPL:概要
下一篇
PHP SPL:SplObjectStorage
系列文
花式PHP31

尚未有邦友留言

立即登入留言