PHP中clone关键字和__clone()方法的使用(实例详解)

在之前的文章中给大家带来了《PHP中的命名空间定义与使用(实例详解)》,其中详细的介绍了PHP中的命名空间的定义与使用,本篇继续给大家看一看PHP中的相关知识,关于clone关键字的使用。希望对大家有帮助!

在之前的文章中给大家带来了《PHP中的命名空间定义与使用(实例详解)》,其中详细的介绍了PHP中的命名空间的定义与使用,本篇继续给大家看一看PHP中的相关知识,关于clone关键字的使用。希望对大家有帮助!

PHP中clone关键字和__clone()方法的使用(实例详解)

php入门到就业线上直播课:进入学习API 文档、设计、调试、自动化测试一体化协作工具:点击使用

在我们之前的学习中,有很多的关键字,比如$this、$new之类的,今天我们继续来看一下在PHP中也算比较常用到的关键字clone克隆关键字。在学习克隆关键字之前,我们需要知道PHP中的对象模型是通过引用来调用对象的,但是又是偶需要建议一个对象的副本,目的就是想再原有对象改变的时候能够不影响到对象副本。

这时候如果使用new关键字是可以重新创建对象,然后再给属性赋上相同的值,也是可以起到新建副本的作用,但是这种方法不仅麻烦而且容易出错,这时候就希望PHP能有一个完全一样的对象,而且这两个还不是互相干扰的,也就是我们想的克隆。那应该怎样去实现呢?不慌,接着看。

clone关键字

我们希望有一个能够和原本对象互不干扰的副本,在PHP中通过clone关键字就可以实现克隆对象了。

clone关键字的语法格式如下:

克隆对象名称 = clone 原对象名称;登录后复制

你可以把克隆这个动作理解为,把对象的内存区域进行复制,赋值后的对象与原对象之间是相互独立的。并且他们之间的成员方法、属性和值都是完全相同的。

接下来我们通过一个简单的实例来看一下clone的能力吧,示例如下:

study1 = $study1;
$this -> study2 = $study2;
}
public function output(){
echo $this -> study1.;,;. $this -> study2.;;;
}
}
$obj = new father(;好好学习;, ;天天向上;);
$obj2 = clone $obj;//克隆$obj
$obj -> output();
$obj2 -> output();
echo ;;;
var_dump($obj);
var_dump($obj2);
?>登录后复制

输出结果:

PHP中clone关键字和__clone()方法的使用(实例详解)

其中我们需要注意的是,如果使用=将一个对象赋值给一个变量,那么这时得到的将是一个对象的引用,通过这个变量更改属性的值将会影响原来的对象。所以还是得用clone,更改属性值不会影响到原来的对象。

通过上述实例,我们已经知道应该如何去克隆一个对象来为我们所用了,但是对象克隆成功后,他的属性、成员方法以及值都是和原对象一模一样完全相同的,那这时候我们光说更改属性不会影响到原来的对象,但是应该怎样去给克隆后的副本成员属性重新赋值呢?这时候我们就要用到PHP魔术方法中的__clone()方法。

__clone()方法

PHP中__clone()方法是不能够直接调用的,有clone才有__clone(),只有通过clone关键字克隆了一个对象的时候,才能够通过这个克隆出来的对象来调用__clone()方法。

这时候再用到clone创建副本的时候,就需要注意了,PHP会检查__clone()是否存在。

要是不存在的话,PHP会默认赋值对象的全部属性;如果__clone()存在,也就是定义过了,那么也就会负责了新对象的属性。

加下来我们通过一个实例来看一下,实例如下:

name = $name;
$this -> url = $url;
}
public function output(){
echo $this -> name.;,;.$this -> url.;;;
}
public function __clone(){//通过__clone()来更改新对象的属性
$this -> name = ;福如东海;;
$this -> url = ;寿比南山;;
}
}
$obj = new father(;好好学习;, ;天天向上;);
$obj2 = clone $obj;
$obj -> output();
$obj2 -> output();
?>登录后复制

输出结果:

PHP中clone关键字和__clone()方法的使用(实例详解)

由上述实例,可以看出__clone() 方法不需要任何参数。其中我们还有一点可以知道的就是,想要禁止克隆的话,只需要在类中设置一个空的,访问权限为 private(私有的)的 __clone() 方法的话,就可以起到禁止克隆的目的了。

大家如果感兴趣的话,可以点击《PHP视频教程》进行更多关于PHP知识的学习。

PHP中的clone和new性能比较(代码示例)

转载2019-05-07 09:12:482812 + php学习QQ群(点击入群)clone和new本不应该放在一起比较,它们的作用是不同的。但可能有一些场景下,可以用clone也可以用new,那么这时候我们选哪个呢?

我编写了两个测试,第一个是声明一个空类,第二个是带构造方法、属性的类。另外,我还加入了 PHP 序列化的测试。

国际惯例,直接上代码,一目了然。

代码

<?php
define('TEST_COUNT', 10000);

function test($name, $callable)
{
$time = microtime(true);
$callable();
echo $name, ' time: ', microtime(true) – $time, 's', PHP_EOL;
}
// 空的类
class A
{

}
function test1()
{
echo '空的类:', PHP_EOL;
$a = new A;
test('A clone', function() use($a){
for($i = 0; $i < TEST_COUNT; ++$i)
{
$obj = clone $a;
}
});
test('A new', function(){
for($i = 0; $i 1,
'name' => 'imi 框架牛逼',
'description' => 'IMI 是一款基于 Swoole 开发的协程 PHP 开发框架,拥有常驻内存、协程异步非阻塞IO等优点。',
'url' => 'https://www.imiphp.com',
];
$a = new B($constructData);
test('B clone', function() use($a){
for($i = 0; $i < TEST_COUNT; ++$i)
{
$obj = clone $a;
}
});
test('B new', function() use($a){
for($i = 0; $i data);
}
});
$serialize = serialize($a);
test('B unserialize', function() use($serialize){
for($i = 0; $i < TEST_COUNT; ++$i)
{
$obj = unserialize($serialize);
}
});
}
test2();登录后复制

运行结果

空的类:

A clone time: 0.0015249252319336s
A new time: 0.00090503692626953s
A unserialize time: 0.005108118057251s登录后复制

带构造方法、属性的类:

B clone time: 0.00072503089904785s
B new time: 0.0015559196472168s
B unserialize time: 0.0084571838378906s登录后复制

结论

从空类的测试结果来看,new的性能更高。

从带构造方法、属性的类测试结果来看,clone的性能要比new带上构造参数的性能高不少。

序列化一如既往地性能堪忧,能不用就别用。

所以,我们该用clone的地方还是乖乖用吧,性能并不差。

php入门到就业线上直播课:立即学习全程直播 + 实战授课 + 边学 + 边练 + 边辅导

以上就是PHP中的clone和new性能比较(代码示例)的详细内容,更多请关注钦钦技术栈其它相关文章!

转载至:php中文网【www.php.cn】

版权声明:本文(即:原文链接:https://www.qin1qin.com/catagory/27524/)内容由互联网用户自发投稿贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 630367839@qq.com 举报,一经查实,本站将立刻删除。

(0)
上一篇 2022-09-30 3:50:28
下一篇 2022-09-30 3:51:39

软件定制开发公司

相关阅读

发表回复

登录后才能评论
通知:禁止投稿所有关于虚拟货币,币圈类相关文章,发现立即永久封锁账户ID!