PHP编程中的__clone()方法使用详解


Posted in PHP onNovember 27, 2015

可以在对象类中定义一个__clone()方法来调整对象的克隆行为。此方法的代码将在克隆操作期间执行。除了将所有现有对象成员复制到目标对象之外,还会执行__clone()方法指定的操作。下面修改Corporate_Drone类,增加以下方法:

function __clone() { 
 $this->tiecolor = "blue";
}

之后,创建一个新的Corporate_Drone对象,增加employeeid成员的值,克隆这个对象,然后输出一些数据,从而显示克隆对象的tiecolor确实是通过__clone()方法设置的。示例代码:

<?php
 // Create new corporatedrone object
  $drone1 = new corporatedrone();
 
 // Set the $drone1 employeeid member
  $drone1->setEmployeeID("12345");
 
 // Clone the $drone1 object
  $drone2 = clone $drone1;
 
 // Set the $drone2 employeeid member
  $drone2->setEmployeeID("67890");
 
 // Output the $drone1 and $drone2 employeeid members
  echo "drone1 employeeID: ".$drone1->getEmployeeID()."<br />";
  echo "drone2 employeeID: ".$drone2->getEmployeeID()."<br />";
  echo "drone2 tiecolor: ".$drone2->getTiecolor()."<br />";
?>

程序运行结果

drone1 employeeID: 12345
drone2 employeeID: 67890
drone2 tiecolor:

再来一个小例子:

<?php
class Fruit {
 private $name = "水果";
 private $color = "颜色";
 
 public function setName($name){
 $this->name = $name;
 }
 
 public function setColor($color){
 $this->color = $color;
 }
 
 function showColor(){
 return $this->color.'的'.$this->name."<br />";
 }
 
 function __destruct(){
 echo "被吃掉了(对象被回收) <br />"; 
 }
}

$apple = new Fruit();
$apple->setName("大苹果");
$apple->setColor("红色");
echo $apple->showColor();

$clone_apple = $apple;
$clone_apple->setName("小苹果");
$clone_apple->setColor("青色");

echo $clone_apple->showColor();
?>

上面只是将一个类赋值给另一个类,所以此时内存中仍是一个对象。

<?php
class Fruit {
 private $name = "水果";
 private $color = "颜色";
 
 public function setName($name){
 $this->name = $name;
 }
 
 public function setColor($color){
 $this->color = $color;
 }
 
 function showColor(){
 return $this->color.'的'.$this->name."<br />";
 }
 
 function __destruct(){
 echo "被吃掉了(对象被回收) <br />"; 
 }
 function __clone(){
 $this->name = "克隆水果"; 
 }
}

$apple = new Fruit();
$apple->setName("大苹果");
$apple->setColor("红色");
echo $apple->showColor();

$clone_apple = clone $apple;
$clone_apple->setColor("青色");

echo $clone_apple->showColor();
?>

clone方法克隆出了一个新的类,所以此时内存中有两个对象。

php的__clone()方法对一个对象实例进行的浅复制,对象内的基本数值类型进行的是传值复制,而对象内的对象型成员变量,如果不重写__clone方法,显式的clone这个对象成员变量的话,这个成员变量就是传引用复制,而不是生成一个新的对象.如下面一个例子的第28行注释所说

<?php
  class Account {
    public $balance;
    
    public function __construct($balance) {
      $this->balance = $balance;
    }
  }
 
  class Person {
    private $id;
    private $name;
    private $age;
    public $account;
    
    public function __construct($name, $age, Account $account) {
      $this->name = $name;
      $this->age = $age;
      $this->account = $account;
    }
    
    public function setId($id) {
      $this->id = $id;
    }
    
    public function __clone() {  #复制方法,可在里面定义再clone是进行的操作
      $this->id = 0;
      $this->account = clone $this->account;  #不加这一句,account在clone是会只被复制引用,其中一个account的balance被修改另一个也同样会被修改
    }
  }
  
  $person = new Person("peter", 15, new Account(1000));
  $person->setId(1);
  $person2 = clone $person;
  
  $person2->account->balance = 250;
  
  var_dump($person, $person2);
  
 ?>

输出:

object(Person)#1 (4) { ["id":"Person":private]=> int(1) ["name":"Person":private]=> string(5) "peter" ["age":"Person":private]=> int(15) ["account"]=> object(Account)#2 (1) { ["balance"]=> int(1000) } } object(Person)#3 (4) { ["id":"Person":private]=> int(0) ["name":"Person":private]=> string(5) "peter" ["age":"Person":private]=> int(15) ["account"]=> object(Account)#4 (1) { ["balance"]=> int(250) } }
PHP 相关文章推荐
php 无限级缓存的类的扩展
Mar 16 PHP
php实现的仿阿里巴巴实现同类产品翻页
Dec 11 PHP
php URL验证正则表达式
Jul 19 PHP
php错误、异常处理机制(补充)
May 07 PHP
php判断正常访问和外部访问的示例
Feb 10 PHP
php根据年月获取季度的方法
Mar 31 PHP
PHP程序中使用adodb连接不同数据库的代码实例
Dec 19 PHP
php实现登陆模块功能示例
Oct 20 PHP
php PDO异常处理详解
Nov 20 PHP
PHP四种排序算法实现及效率分析【冒泡排序,插入排序,选择排序和快速排序】
Apr 27 PHP
Yii框架的路由配置方法分析
Sep 09 PHP
redis+php实现微博(三)微博列表功能详解
Sep 23 PHP
PHP通过反射动态加载第三方类和获得类源码的实例
Nov 27 #PHP
基于php实现随机合并数组并排序(原排序)
Nov 26 #PHP
PHP随手笔记整理之PHP脚本和JAVA连接mysql数据库
Nov 25 #PHP
php实现遍历多维数组的方法
Nov 25 #PHP
WordPress迁移时一些常见问题的解决方法整理
Nov 24 #PHP
基础的WordPress插件制作教程
Nov 24 #PHP
优化WordPress的Google字体以加速国内服务器上的运行
Nov 24 #PHP
You might like
PHP之APC缓存详细介绍 apc模块安装
2014/01/13 PHP
CentOS下PHP安装Oracle扩展
2015/02/15 PHP
php die()与exit()的区别实例详解
2016/12/03 PHP
如何优雅的使用 laravel 的 validator验证方法
2018/11/11 PHP
php使用filter_var函数判断邮箱,url,ip格式示例
2019/07/06 PHP
javascript IE中的DOM ready应用技巧
2008/07/23 Javascript
Riot.js 快速的JavaScript单元测试框架
2009/11/09 Javascript
JavaScript返回网页中超链接数量的方法
2015/04/03 Javascript
jQuery实现灰蓝风格标准二级下拉菜单效果代码
2015/08/31 Javascript
jquery实现简洁文件上传表单样式
2015/11/02 Javascript
getElementById().innerHTML与getElementById().value的区别
2016/10/27 Javascript
微信小程序购物商城系统开发系列-目录结构介绍
2016/11/21 Javascript
原生js实现电商侧边导航效果
2017/01/19 Javascript
Vue学习笔记进阶篇之vue-cli安装及介绍
2017/07/18 Javascript
AngularJS模糊查询功能实现代码(过滤内容下拉菜单排序过滤敏感字符验证判断后添加表格信息)
2017/10/24 Javascript
Vue中添加手机验证码组件功能操作方法
2017/12/07 Javascript
vue 基于abstract 路由模式 实现页面内嵌的示例代码
2020/12/14 Vue.js
Vue 修改网站图标的方法
2020/12/31 Vue.js
[01:35]2014DOTA2西雅图邀请赛 专访狐狸妈青春献给刀塔
2014/07/08 DOTA
python实现画五角星和螺旋线的示例
2019/01/20 Python
pyqt 实现为长内容添加滑轮 scrollArea
2019/06/19 Python
Python调用钉钉自定义机器人的实现
2020/01/03 Python
tensorflow 初始化未初始化的变量实例
2020/02/06 Python
python 模块导入问题汇总
2021/02/01 Python
HTML5触摸事件(touchstart、touchmove和touchend)的实现
2020/05/08 HTML / CSS
多媒体编辑专业毕业生推荐信
2013/11/05 职场文书
红旗团支部事迹材料
2014/01/27 职场文书
人事经理岗位职责
2014/04/28 职场文书
诉前财产保全担保书
2014/05/20 职场文书
村道德模范事迹材料
2014/08/28 职场文书
处级干部反四风个人对照检查材料思想汇报
2014/09/27 职场文书
催款律师函范文
2015/05/27 职场文书
三八节祝酒词
2015/08/11 职场文书
详解vue中v-for的key唯一性
2021/05/15 Vue.js
自动在Windows中运行Python脚本并定时触发功能实现
2021/09/04 Python
2022新作动画《福星小子》释出宣传影片 加入内田真礼&宫野真守配音演出
2022/04/08 日漫