PHP 深度克隆对象
Posted
技术标签:
【中文标题】PHP 深度克隆对象【英文标题】:PHP deep clone object 【发布时间】:2012-06-05 14:29:38 【问题描述】:场景:从数据库中获取一个电子邮件模板,并遍历收件人列表,为每个收件人个性化电子邮件。
我的电子邮件模板作为嵌套对象返回。它可能看起来像这样:
object(stdClass)
["title"] => "Event Notification"
["sender"] => "notifications@mysite.com"
["content"] => object(stdClass)
["salutation"] => "Dear %%firstname%%,"
["body"] => "Lorem ipsum %%recipient_email%% etc etc..."
然后我遍历收件人,将此 $email 对象传递给 Personalise() 函数:
foreach( $recipients as $recipient )
$email_body = personalise( $email, $recipient );
//send_email();
当然,问题是我需要通过引用传递 $email 对象,以便它替换个性化标签 - 但如果我这样做,原始对象将被更改并且不再包含个性化标签。
据我了解,克隆在这里对我没有帮助,因为它只会创建一个浅拷贝:电子邮件对象中的内容对象不会被克隆。
我读过关于使用 unserialize(serialize($obj)) 解决这个问题的文章 - 但我读到的所有内容都表明这是一个很大的性能损失。
所以,两个终于解决了我的两个问题:
-
这里是 unserialize(serialize($obj)) 一个合理的解决方案吗?
还是我把整件事都搞错了?我有什么不同的方式吗
可以生成该电子邮件对象的个性化副本吗?
【问题讨论】:
我发现 swiftmailer 在使用装饰器插件 (swiftmailer.org/docs/plugins.html#decorator-plugin) 方面做得很好,而且它在标题方面做得很好;我们的垃圾邮件结果非常低。 【参考方案1】:您可以将__clone()
方法添加到您的电子邮件类。当通过 clone() 克隆此类的实例时会自动调用它。在此方法中,您可以手动添加模板。
例子:
class email
__clone()
$this->template = new template();
.
unserialize(serialize($object)); // would be another solution...
【讨论】:
【参考方案2】:另一个更通用、更强大的解决方案:MyCLabs\DeepCopy。
它有助于创建深层副本,而不必重载 __clone
(如果您有很多不同的对象,这可能是很多工作)。
【讨论】:
这是要走的路,尤其是在使用 ORM(即 Doctrine2)时。以上是关于PHP 深度克隆对象的主要内容,如果未能解决你的问题,请参考以下文章