許多開發者測試 unset($a) 後發現 memory_get_usage() 數值未降回初始值,甚至有人結論「PHP unset 不釋放記憶體」。實際上,這 32 位元組的差異往往源自隱性分配(如輸出緩衝區的 Header),而非 unset 失效。
emalloc/efree 管理記憶體池,向 OS 申請大塊記憶體後自行切割分配,釋放時歸入空閒列表而非還給 OS。memory_get_usage(true) 回傳系統分配總量(real size),false(預設)回傳實際使用量。測試時應加 true 觀察真實變化。memory_get_usage() 不扣除此部分,導致視覺上「未釋放」。<?php
var_dump("I am www.7di.net"); // 輸出函數佔用緩衝區
var_dump(memory_get_usage());
$a = "laruence";
var_dump(memory_get_usage());
unset($a);
var_dump(memory_get_usage());
輸出顯示:前後 memory_get_usage() 差值為 0。證實這 32 位元組是 var_dump 輸出時佔用的 Header 空間,unset 確實正常釋放了變數記憶體。
PHP 陣列與符號表底層皆為 Hashtable。當大量變數寫入符號表導致擴容後,即使全部 unset,Hashtable 本身佔用的記憶體不會縮小。範例:建立 100 個變數再全部 unset,記憶體下降但未回初始值,差額即為符號表結構佔用。
unset,有助於降低請求高峰記憶體佔用。$arr = [] 而非單純 unset 元素。理解 PHP 記憶體管理機制,能避免過度優化或誤判效能瓶頸,編寫更穩健的高併發應用。