php之clone 复制对象以及__clone魔术方法
如果错误和不足请给予指出,谢谢~
(⊙_⊙)
在开始使用clone之前我们下先看以下一个小例子:
<?php
//首先定义一个test一个类
class Testclass { //成员变量是$value1 public $value1;
}
//随后new一个obj1
$obj1 = new Testclass();
//复制成员变量的值为qqq
$obj1->value1 = "qqq";
//我们使用赋值符号给左边obj2赋值obj1
$obj2 = $obj1;
//我们在这里把obj2的的value1复制为eee
$obj2->value1 ="eee"; //随后我们打印出两者的值
var_dump($obj1);
echo '<br/>';
var_dump($obj2);
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
为了查看方便,我把那个解释写在了注释=。=。(这句话总感觉怪怪的)
我们运行一下,发现如下结果:
是不是两者的值都是一样的?
那是因为(借用php手册的话就是):当对象被复制后,PHP 5 会对对象的所有属性执行一个浅复制(shallow copy)。所有的引用属性 仍然会是一个指向原来的变量的引用。
其实在这里就是obj1给了obj2它的地址,就和引用一样,obj2指向了obj1,所以导致两者所执行的操作将会收到影响。那么该如何解决这样情况呢?当然是使用clone了;列如下代码:
<?php
//首先定义一个test一个类
class Testclass { //成员变量是$value1 public $value1;
}
//随后new一个obj1
$obj1 = new Testclass();
//复制成员变量的值为qqq
$obj1->value1 = "qqq";
//在这里我们使用clone来赋值obj1
$obj2 =clone $obj1;
//我们在这里把obj2的的value1复制为eee
$obj2->value1 ="eee"; //随后我们打印出两者的值
var_dump($obj1);
echo '<br/>';
var_dump($obj2);
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
注意看这一段代码:
$obj2 =clone $obj1;
- 1
在这里使用了clone,这样就会没事了,看如下运行结果:
是否发现两者并没有相互影响呢?
好了,在这里已经完成了基本的clone的讲解了,现在我们来深入一下(抽根烟压压惊。。。 ( ´´ิ∀´ิ` ) )
我们接下来看看一个例子:
<?php
//首先定义一个test一个类
class Testclass { //成员变量是$value1 public $value1;
}
//在这里是定义了一个变量
$vlaue_1='bbj';
//随后new一个obj1
$obj1 = new Testclass();
//引用value_1的值,注意,是引用
$obj1->value1 = &$vlaue_1;
//在这里我们使用clone来赋值obj1
$obj2 =clone $obj1;
//我们在这里把obj2的的value1复制为eee
$obj2->value1 ="eee"; //随后我们打印出两者的值
var_dump($obj1);
echo '<br/>';
var_dump($obj2);
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
我们的代码和之前的差不多,我们主要看这一行:
//引用value_1的值,注意,是引用
$obj1->value1 = &$vlaue_1;
- 1
- 2
注意在此是引用哟。
我们看下运行结果:
是否发现我在obj2改变了value1值之后obj1的值也会改变?因为在这里obj1赋值成员变量的时候使用了&取址。将会成为一个引用的状态。那么我们如果想要把这个值不守clone出来的对象的值影响该怎么办呢?
那么在这里我们只需要在此clone一下这个成员变量就好了,该如何clone了?那么我们现在就可以使用我们的魔法方法__clone了。
首先我们来说说__clone()在什么状态下触发:
当我们有clone操作的时候将会除非这个类里面的__clone方法。那么把我们的成员变量在__clone方法里面clone一下就好了,如下代码演示:
注:clone只能用于对象克隆,对象复制。记住,如果你clone一个非对象变量将会报错no obj。。。
以下例子是我从网上找的一个例子,感觉不错,这里将用这个例子来讲解魔法方法__clone的使用:
本来这个是没有注释的,我顺便把解释丢到了里面,这样强制clone后就不会指向原来的对象了。
<?php
class testClass
{
public $str_data;//这里是一个非对象类型
public $obj_data;//在这里这是一个对象,可以看下面将会给一个对象给他
//使用clone的时候触发
public function __clone() { $this->obj_data = clone $this->obj_data;//这个对象将会被克隆,会被强制复制,这样就不会指向原来的对象了
}
}
//new一个datatime对给datatimeobj
$dateTimeObj = new DateTime("2014-07-05", new DateTimeZone("UTC"));
$obj1 = new testClass();//new一个testclass
$obj1->str_data ="aaa"; //复制aaa
$obj1->obj_data = $dateTimeObj; //给obj_data一个对象datetimeobj
$obj2 = clone $obj1; //克隆obj1给obj2
var_dump($obj1); // str_data:"aaa" obj_data:"2014-07-05 00:00:00"
var_dump($obj2); // str_data:"aaa" obj_data:"2014-07-05 00:00:00"
$obj2->str_data ="bbb"; //obj2给一个值bbb给strdata
$obj2->obj_data->add(new DateInterval('P10D'));//objdata改变objdata的值
var_dump($obj1); // str_data:"aaa" obj_data:"2014-07-05 00:00:00"
var_dump($obj2); // str_data:"aaa" obj_data:"2014-07-15 00:00:00"
var_dump($dateTimeObj); //"2014-07-05 00:00:00"
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
以上就是clone的使用方法了=。=。。。
如果错误请给予指出,谢谢~
文章来源: i1bit.blog.csdn.net,作者:A757291228,版权归原作者所有,如需转载,请联系作者。
原文链接:i1bit.blog.csdn.net/article/details/57457498
- 点赞
- 收藏
- 关注作者
评论(0)