Http://www.cnblogs.com/taijun/p/4208008.html
Let's talk about deep-copy and shallow-copy popular understanding
Deep copy: Assignment value is fully copied, full copy, change to one of them, does not affect another
Shallow copy: When assigned, the reference is assigned, which is equivalent to taking an alias. One of the modifications will affect the other
in PHP, = when assigned, the normal object is a deep copy, but to the object it is a shallow copy. In other words, the assignment of an object is a reference assignment . (When an object is passed as a parameter, it is also a reference pass, regardless of whether the parameter is preceded by A & symbol in the function definition)
PHP4, the object's = assignment is to implement a copy, so there are many problems, unknowingly we may copy many copies.
In php5, the = assignment and delivery of an object are references. To implement a copy copy, PHP provides a clone function implementation.
Clone has completely copied a copy. But clone, we may not want to copy all the contents of the source object, then we can use __clone to manipulate.
In __clone (), we can do some things. Note that these operations, that is, the __clone function, are on the Copy object that is acting on the copy
12345678910111213141516171819 |
<?php
//普通对象赋值,深拷贝,完全值复制
$m
= 1;
$n
=
$m
;
$n
= 2;
echo
$m
;
//值复制,对新对象的改变不会对m作出改变,输出 1.深拷贝
echo
PHP_EOL;
/*==================*/
//对象赋值,浅拷贝,引用赋值
class
Test{
public
$a
=1;
}
$m
=
new
Test();
$n
=
$m
;
//引用赋值
$m
->a = 2;
//修改m,n也随之改变
echo
$n
->a;
//输出2,浅拷贝
echo
PHP_EOL;
?>
|
PHP provides the clone function to implement a copy of the object, because it is referenced when the object is assigned, and if you want to replicate the value.
However, there is a problem with the clone function, when cloning an object, the normal property of the original object can be copied, but the object property of the source object is assigned value or reference assignment, shallow copy.
12345678910111213141516171819202122232425262728 |
<?php
class Test{
public
$a
=1;
}
class
TestOne{
public
$b
=1;
public
$obj
;
//包含了一个对象属性,clone时,它会是浅拷贝
public
function
__construct(){
$this
->obj =
new
Test();
}
}
$m =
new
TestOne();
$n
=
$m
;
//这是完全的浅拷贝,无论普通属性还是对象属性
$p
=
clone
$m
;
//普通属性实现了深拷贝,改变普通属性b,不会对源对象有影响
$p
->b = 2;
echo
$m
->b;
//输出原来的1
echo
PHP_EOL;
//对象属性是浅拷贝,改变对象属性中的a,源对象m中的对象属性中a也改变
$p
->obj->a = 3;
echo
$m
->obj->a;
//输出3,随新对象改变
?>
|
There are two ways to achieve a true deep copy of an object:
Write the Clone function: the following
1234567891011121314151617181920212223242526272829303132 |
<?php
class
Test{
public
$a
=1;
}
class
TestOne{
public
$b
=1;
public
$obj
;
//包含了一个对象属性,clone时,它会是浅拷贝
public
function
__construct(){
$this
->obj =
new
Test();
}
//方法一:重写clone函数
public
function
__clone(){
$this
->obj =
clone
$this
->obj;
}
}
$m
=
new
TestOne();
$n
=
clone
$m
;
$n
->b = 2;
echo
$m
->b;
//输出原来的1
echo
PHP_EOL;
//可以看到,普通属性实现了深拷贝,改变普通属性b,不会对源对象有影响
//由于改写了clone函数,现在对象属性也实现了真正的深拷贝,对新对象的改变,不会影响源对象
$n
->obj->a = 3;
echo
$m
->obj->a;
//输出1,不随新对象改变,还是保持了原来的属性
?>
|
It is inconvenient to overwrite the __clone () function, and you have to have the object properties in this class in each class in __clone () one by one clone
The second method, which is implemented by serialization deserialization, enables the deep copy of the object to be simple, without modifying the class
123456789101112131415161718192021222324252627282930 |
<?php
class
Test{
public
$a
=1;
}
class
TestOne{
public
$b
=1;
public $obj
;
//包含了一个对象属性,clone时,它会是浅拷贝
public
function
__construct(){
$this
->obj =
new
Test();
}
}
$m
=
new
TestOne();
//方法二,序列化反序列化实现对象深拷贝
$n
= serialize(
$m
);
$n
= unserialize(
$n
);
$n
->b = 2;
echo
$m
->b;
//输出原来的1
echo
PHP_EOL;
//可以看到,普通属性实现了深拷贝,改变普通属性b,不会对源对象有影响
$n
->obj->a = 3;
echo
$m
->obj->a;
//输出1,不随新对象改变,还是保持了原来的属性,可以看到,序列化和反序列化可以实现对象的深拷贝
?>
|
There is a third method, in fact, similar to the second, Json_encode and then Json_decode, the implementation of the assignment
Deep copy and shallow copy of PHP