【问题标题】:Implementing deep clone()实现深度克隆()
【发布时间】:2017-09-01 15:40:48
【问题描述】:

考虑一些 OOP 语言(它是哪一种并不重要)并假设语言创建者想要为每个类添加一个 deep clone() 方法。此外,假定堆被实现为树。

语言创建者应该如何实现它?

所以基本上我们可以(在编译时自动)实现一个 clone() 方法并将其添加到适当的函数虚拟表中。 它将 malloc() 在运行时已知的正确大小并从源复制到目标。最后,它会返回指向 malloced 内存的指针。

如果一个字段是指向某个对象的指针,我们将激活它的 clone() 并将结果作为该字段的值。

如果堆不是“基于树的”会出现什么问题?
所以我真的不知道答案是什么。我的意思是,为什么堆是如何实现的?我很乐意在这里提供帮助。

谢谢。

【问题讨论】:

    标签: oop memory compiler-construction heap-memory


    【解决方案1】:

    只要对象结构是非循环的,即形成一棵树,您描述的算法就可以正常工作。然后,确实可以对对象进行浅层克隆,然后使用相同的技术继续更新引用其他对象的字段。

    但是,如果存在循环(即对象结构没有形成树),算法将永远运行。在最简单的情况下,初始对象o 引用自身:o -> o。当创建一个浅克隆c1 时,新对象仍然引用旧对象:c1 -> o。此外,旧对象没有改变,即我们有c1 -> o -> o。根据该算法,应创建从克隆引用的对象的克隆。因为这是一个新对象,所以它不同于c1。所以,图片变成了c1 -> c2 -> o。这已经是错误的,因为深度克隆应该创建的是c1 -> c1。坏消息是c2 现在也成为处理对象。所以,我们得到c1 -> c2 -> c3 -> o,等等。算法永远循环(直到没有更多的内存来创建新对象)。

    为了使算法正常工作,它应该跟踪哪些旧对象已被处理以及为它们创建了哪些新对象。然后,与其盲目地对引用的对象进行新的克隆,不如检查一个旧对象是否已经被克隆,如果是,则使用这个克隆而不是创建一个新的。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2010-12-14
      • 1970-01-01
      • 2011-07-26
      • 2019-02-27
      • 1970-01-01
      • 2010-09-09
      • 1970-01-01
      相关资源
      最近更新 更多