我計畫將物件序列化和反序列化作為儲存方式,並且我的應用程式可以方便地將大量物件分組到單個要序列化的物件中。但是,這提出了一些我需要回答的問題
假設我計畫序列化的父物件是 "A",而我儲存在其中的物件將會是 A(a-z)。如果我將 A(b) 傳遞給 A(c),這會通過參考傳遞。因此,如果 A(c) 執行會影響 A(b) 值的動作,這也會更新儲存在 A 中的原始 A(b)。太棒了!
但是,當我序列化 A 時會發生什麼?其中 A(c) 引用了 A(b),然後我進行反序列化?A(c) 會擁有 A(b) 的新獨立副本,還是仍然會參考儲存在 A 中的 A(b)?
答案是,PHP 5.5 和 PHP 7 都會追蹤在反序列化過程中,某個東西是否是它已經「重新建立」的物件的參考,請參閱以下範例
<?php
class foo {
protected $stored_object;
protected $stored_object2;
protected $stored_value;
public function __construct($name, $stored_value) {
$this->store_value($stored_value);
echo 'Constructed: '.$name.' => '.$stored_value.'<br/>';
}
public function store_object(foo $object) {
$this->stored_object = $object;
}
public function store_object2(foo $object) {
$this->stored_object2 = $object;
}
public function store_value($value) {
$this->stored_value = $value;
}
public function stored_method($method, array $parameters) {
echo 'Call stored method: '.$method.'{ <br/>';
call_user_func_array(array($this->stored_object, $method), $parameters);
echo '} <br/>';
}
public function stored_method2($method, array $parameters) {
echo 'Call stored method 2: '.$method.'{ <br/>';
call_user_func_array(array($this->stored_object2, $method), $parameters);
echo '} <br/>';
}
public function echo_value() {
echo 'Value: '.$this->stored_value.'<br/>';
}
}
$foo = new foo('foo', 'Hello!'); $new_foo = new foo('new_foo', 'New Foo 2!'); $third_foo = new foo('third_foo', 'Final Foo!'); $foo->store_object($new_foo);
$foo->store_object2($third_foo);
$foo->stored_method('store_object', array($third_foo)); $serialized = serialize($foo);
unset($foo);
unset($new_foo);
unset($third_foo);
$unserialized_foo = unserialize($serialized);
$unserialized_foo->stored_method2('store_value', array('Super Last Foo!')); $unserialized_foo->echo_value(); $unserialized_foo->stored_method('echo_value', array());
$unserialized_foo->stored_method('stored_method', array('echo_value', array()));
?>
根據最後一行,A(b) 中 A(c) 的「副本」仍然是對儲存在 A 中的原始 A(b) 的參照,即使在還原序列化之後也是如此。