资讯专栏INFORMATION COLUMN

PHP|关于对象复制的一些事

svtter / 1356人阅读

摘要:先看对象复制的代码在及以后的版本,指向同一个对象。在中,对象的赋值和传递都是通过引用进行的。当我们需要一个对象的副本时,可以这么做通过关键字,使用值复制方式新生成一个对象。但是这有一个问题,对象中的某些数据,比如,我不想是一样的。

先看对象复制的代码

class CopyMe{}
$first = new CopyMe();
$second = $first;

在PHP5及以后的版本,$first & $second指向同一个对象。

在PHP中,对象的赋值和传递都是通过引用进行的。

当我们需要一个对象的副本时,可以这么做:

class CopyMe{}
$first = new CopyMe();
$second = clone $first;

通过clone关键字,使用值复制方式新生成一个对象。

但是这有一个问题,对象中的某些数据,比如id,我不想是一样的。但是clone是做不到的。

这时我们可以通过实现一个特殊的方法__clone()来达到这个目的。当一个对象调用clone关键字时,其__clone()方法就会被自动调用。

class Person
{
    public private $id;
    
    public function __construct() {}
    
    public function setId($id) {
        $this->id = $id;
    }

    public function __clone() {
        $this->id = 0;
    }
}

$person = new Person();
$person->setId(343);
$person2 = clone $person;

这样的赋值属于浅复制(shallow copy),可以保证所有基本数据类型的属性被完全复制。

如果我们不希望对象的属性的属性被共享,例如:

class Account
{
    public $balance;
    public function __construct($balance) {
        $this->balance = $balance;
    }
}

class Person
{
    private $name;
    private $age;
    private $id;
    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() {
        $this->id = 0;
    }
}

$person = new Person("bob", 43, new Account(200));
$person->setId(433);
$person2 = clone $person;

$person->account->balance += 10;
print $person2->account->balance;

得到的结果: 210

实际上我并不想让$person2的账户价格受到另一个对象的影响。

可以显式的在__clone方法中复制指向的对象。

function __clone() {
    $this->id = 0;
    $this->account = clone $this->account;
}

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/21653.html

相关文章

  • 【面试】Java基础中那些-One

    摘要:前言面试中对于技术职位,一般分笔试与面谈,如果面试官的一些小问题你可以立马找到对应的知识点扩展开来,那么这就是你的优势,本系列将讲述一些面试中的事,不会很详细,但是应该比较全面吧。 前言 面试中对于技术职位,一般分笔试与面谈,如果面试官的一些小问题你可以立马找到对应的知识点扩展开来,那么这就是你的优势,本系列将讲述一些java面试中的事,不会很详细,但是应该比较全面吧。 主要内容 说到...

    Stardustsky 评论0 收藏0
  • PHP 引用是个坑,请慎用

    摘要:发布时最大的变动是对象处理方式。这很容易被误解为引用,但是存储器的引用与引用是完全不同的概念。使用引用是一件不好的事情,除了引用本身不好,并且还会使性能下降这个事实外,使用引用这种方式会使得代码难以维护。 showImg(https://segmentfault.com/img/remote/1460000014082570); 去年我参加了很多次会议,其中八次会议里我进行了相关发言,...

    dockerclub 评论0 收藏0
  • SegmentFault 技术周刊 Vol.32 - 七夕将至,你对象”还好吗?

    摘要:很多情况下,通常一个人类,即创建了一个具体的对象。对象就是数据,对象本身不包含方法。类是相似对象的描述,称为类的定义,是该类对象的蓝图或原型。在中,对象通过对类的实体化形成的对象。一类的对象抽取出来。注意中,对象一定是通过类的实例化来的。 showImg(https://segmentfault.com/img/bVTJ3H?w=900&h=385); 马上就要到七夕了,离年底老妈老爸...

    李昌杰 评论0 收藏0
  • SegmentFault 技术周刊 Vol.32 - 七夕将至,你对象”还好吗?

    摘要:很多情况下,通常一个人类,即创建了一个具体的对象。对象就是数据,对象本身不包含方法。类是相似对象的描述,称为类的定义,是该类对象的蓝图或原型。在中,对象通过对类的实体化形成的对象。一类的对象抽取出来。注意中,对象一定是通过类的实例化来的。 showImg(https://segmentfault.com/img/bVTJ3H?w=900&h=385); 马上就要到七夕了,离年底老妈老爸...

    Lyux 评论0 收藏0
  • SegmentFault 技术周刊 Vol.32 - 七夕将至,你对象”还好吗?

    摘要:很多情况下,通常一个人类,即创建了一个具体的对象。对象就是数据,对象本身不包含方法。类是相似对象的描述,称为类的定义,是该类对象的蓝图或原型。在中,对象通过对类的实体化形成的对象。一类的对象抽取出来。注意中,对象一定是通过类的实例化来的。 showImg(https://segmentfault.com/img/bVTJ3H?w=900&h=385); 马上就要到七夕了,离年底老妈老爸...

    AaronYuan 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<