/**
* 电视机类
*/
class Television
{
/**
* 电视机编号
*/
protected $_identity = 0;
/**
* 屏幕高度
*/
protected $_screenLength = 300;
/**
* 屏幕宽度
*/
protected $_screenHight = 200;
/**
* 电视机外观颜色
*/
protected $_color = 'black';
/**
* 遥控器对象
*/
protected $_control = null;
/**
* 构造函数中加载遥控器对象
*/
public function __construct()
{
$this->setControl(new Telecontrol());
}
/**
* 设置遥控器对象
*/
public function setControl(Telecontrol $control)
{
$this->_control = $control;
return $this;
}
/**
* 返回遥控器对象
*/
public function getControl()
{
return $this->_control;
}
/**
* 返回电视外观颜色
*/
public function getColor()
{
return $this->_color;
}
/**
* 设置电视机外观颜色
*/
public function setColor($color)
{
$this->_color = (string)$color;
return $this;
}
/**
* 返回电视机编号
*/
public function getIdentity()
{
return $this->_identity;
}
/**
* 设置电视机编号
*/
public function setIdentity($id)
{
$this->_identity = (int)$id;
return $this;
}
public function __clone()
{
$this->setIdentity(0);
}
}
/**
* 遥控器类
*/
class Telecontrol
{
}
方法1:直接复制对象
//直接复制对象,改变任意一对象属性,其他对象属性也会改变
$tv1 = new Television();
$tv2 = $tv1;
echo 'color of tv1 is: ' . $tv1->getColor();//tv1的颜色是black
echo '<br>';
echo 'color of tv2 is: ' . $tv2->getColor();//tv2的颜色是black
echo '<br>';
//把tv2涂成白色
$tv2->setColor('white');
echo 'color of tv2 is: ' . $tv2->getColor();//tv2的颜色是white
echo '<br>';
echo 'color of tv1 is: ' . $tv1->getColor();//tv1的颜色是white
方法2:通过clone对象方法将属性初始化
//通过clone 方法
$tv1 = new Television();
$tv2 = clone $tv1;
echo 'color of tv1 is: ' . $tv1->getColor();//tv1的颜色是black
echo '<br>';
echo 'color of tv2 is: ' . $tv2->getColor();//tv2的颜色是black
echo '<br>';
//把tv2换成涂成白色
$tv2->setColor('white');
echo 'color of tv2 is: ' . $tv2->getColor();//tv2的颜色是white
echo '<br>';
echo 'color of tv1 is: ' . $tv1->getColor();//tv1的颜色是black
clone方法的优缺点
优点:方法1中,php因为是引用方式,实际复制对象都指向同一对象地址,故改变其中任意对象属性值所有对象的对应属性都会相应改变,为此PHP5提供了一个专门用于复制对象的操作,也就是 clone 。这就是对象复制的由来。
缺点:使用clone操作复制对象时,当被复制的对象有对其它对象的引用的时候,引用的对象将不会被复制。
解决方法1:__clone
public function __clone()
{
//重新设置一个引用对象(引用多少个对象设置多少对象)
$this->setIdentity(0);
$this->setControl(new Telecontrol());
}
解决方法2:利用串行化做深复制
PHP有串行化(serialize)和反串行化(unserialize)函数,我们只需要用serialize()将一个对象写入一个流,然后从流中读回对象,那么对象就被复制了。在Java语言里面,这个过程叫做“冷藏”和“解冻”。