在記憶中 php 簡單變數的拷貝是按值傳遞,陣列和物件的拷貝是按引用傳遞,即通過引用來實現。
簡單變數和物件好理解:
<?php//簡單變數的拷貝
$a = 'human';
$b = $a
;$b = 'cat';
var_dump($a); //
string 'human' (length=5)
// 物件的拷貝
class
a{}$a = new
a();
$b = $a
;$b->name = 'jack';
var_dump($a); //
object(a)[1] public 'name' => string 'jack' (length=4)
物件 $a 和 物件 $b 的記憶體位址指向了同乙個地方,即針對 $a 和 $b 所做的操作都針對同乙個例項。
php 中可以通過 clone 關鍵字按值拷貝物件:
<?php
class a
$a = new a();
$b = clone $a;
$b->name = 'dee';
var_dump($a); // object(a)[1] public 'name' => string 'vardy' (length=5)
var_dump($b); // object(a)[2] public 'name' => string 'dee' (length=3)
陣列:
<?php
// 陣列的拷貝
$a = ['human', 'orc'];
$b = $a;
$b[0] = 'elve';
var_dump($a);
// array (size=2)
// 0 => string 'human' (length=5)
// 1 => string 'orc' (length=3)
這樣看,陣列的拷貝是按值傳遞的.
另乙個例子 陣列的迭代器:
<?php
$a = ['human', 'orc', 'elven', 'undead'];
next($a);
$b = $a; // 此時指標位置也隨著陣列的複製而複製
var_dump(current($a)); // string 'orc' (length=3)
var_dump(current($b)); // string 'orc' (length=3)
當陣列拷貝時,陣列的指標位置也隨著複製。
(next:
current:
<?php
$a = ['human', 'orc', 'elven', 'undead'];
end($a);
next($a); // 陣列指標非法,返回 false
$b = $a;
var_dump(current($a)); // string 'human' (length=5)
var_dump(current($b)); // boolean false
當陣列在拷貝前,指標的位置是非法時,拷貝後分別列印兩個陣列指標所指向的當前單元時,出現了不一樣的情況。
原因是陣列變數發生拷貝後,兩個變數中先發生寫操作的,其指標被初始化,即指向第乙個元素,而 current 方法也會產生寫操作,因此 $a 的陣列指標當前指向的是 'human',而 $b current 方法則返回 false。
以下**同理, $b 首先發生了寫操作:
<?php
$a = ['human', 'orc', 'elven', 'undead'];
end($a);
next($a);
$b = $a;
$b = 'dwarf';
var_dump(current($a)); // boolean false
var_dump(current($b)); // string 'human' (length=5)
解析:陣列的拷貝是值傳遞。php 在管理記憶體方面有乙個機制叫寫時複製(cow,copy on write),保證了變數間複製值不浪費記憶體:當乙個變數的值複製到另乙個變數時,php 沒有為複製值使用更多的記憶體,相反,它會更新符號表來說明兩個變數擁有相同的記憶體塊,所以當執行下面的**時並沒有建立乙個新的陣列:
<?php
$a = ['human', 'orc', 'elven', 'undead'];
$b = $a;
當修改了 $a 或 $b 任意乙個副本時,php 將分配所需的記憶體來進行複製:
$b = 'dwarf';
參考:php基礎語法之陣列和陣列指標
php中引用&的真正理解-變數引用、函式引用、物件引用
programming php 3rd edition
PHP的陣列是按值傳遞及按引用傳遞解析
簡單變數和物件好理解 簡單變數的拷貝 a human b a b cat var dump a string human length 5 物件的拷貝 class a a new a b a b name jack var dump a object a 1 public name string j...
深拷貝和淺拷貝,按值傳遞,按址傳遞
一 深拷貝和淺拷貝 js中的兩種變數型別,即值型別 數值 布林值 null undefined 和引用型別 物件 陣列 函式 深拷貝和淺拷貝只針對引用型別。感覺上淺拷貝就是引用,深拷貝是新建。宗旨就是新生成的物件不改變源資料,不管怎樣實現,都可以理解為深拷貝。深拷貝方式一 變成按值傳遞 深拷貝方式二...
php陣列是值傳遞,物件是引用傳遞
例項 1 陣列值傳遞 function main function change cc main output array 2 2 陣列引用傳遞 function main function change cc main outpout array 1 3 類物件值傳遞 class ppfuncti...