0

我用 AS3(一个 OO Javascript)编码,我正在学习 C++。

似乎在 C++ 中,如果你这样做,instance1 = instance2你就是在复制instance1和命名副本instance2。不像 AS3 那样只有“字符串”和数字被复制,而其他类型被“引用”,所以它们都指向同一个对象(如 C++ 指针)。

所以我的问题是:

假设我有“战地 4”(或任何需要硬件的游戏)的源代码,并且我正在运行游戏主类的一个实例,如下所示:BattleField4 gameInstance = new BattleField4()在游戏运行 5 分钟后,代码执行以下操作:BattleField4 gameCopy = gameInstance.

这是否意味着游戏进度和内存中加载的图形的“完整副本”?

如果游戏将 10Gb 的内存和它的图形加载到 RAM 中,那么之后会加载 20GBgameCopy = gameInstance吗?

感谢您的帮助,我希望我的英语很清楚。

4

6 回答 6

4

在 C++ 中,如果您有一些obj类型为 的对象Type,并且您执行:

obj = newObj;

wherenewObj也是 type 的对象Type,这将调用Type的复制构造函数。那会执行“完全复制”吗?

这取决于如何Type实现复制构造函数。看,在 C++ 中,允许类型选择创建副本时发生的情况。有时,它只是复制内部数据。有时,您必须在该类型中实例化新对象,以便可以正确复制由指针内部保存的较大对象。

有时,我们说有Type问题的有“引用语义”。这意味着通过“复制”Type对象,您得到的是两个独立Type的对象,它们在内部引用相同的数据。也就是说,它们都引用了相同的东西。这是完全有效的,并在许多实用 C++ 类中使用。

有时,我们完全禁止复制。这通常适用于不适合引用语义的对象,并且复制它们会过于繁琐。如果一个游戏有一个巨大的、单一的对象来代表游戏,它要么是不可复制的,要么它的复制构造函数将完全被破坏并且不能正常工作(游戏开发者对这些东西是出了名的懒惰)。

于 2013-08-25T05:43:19.630 回答
3

程序员不这样做。没有一个巨大的类包含绝对的一切,如果有,你也不会复制它。你会传递指针或对它的引用。也就是说,如果你确实有一个疯狂的巨大物体,并且你做到了

CrazyHuge crazy_huge_object_2 = crazy_huge_object;

您将(可能,取决于复制语义)拥有两个疯狂的巨大对象,并且您将花费两倍于原始疯狂的大量内存。

于 2013-08-25T05:38:48.670 回答
0

您的示例都没有显示使用参考。在 C++ 中,值语义是默认值。把它想象成structC# 或 Java 中的一个。

如果您想要引用语义,请使用指针或引用。

于 2013-08-25T05:37:28.170 回答
0

默认情况下,C++ 将按值传递,除非它是作为指针传递的 vanilla 数组。这与大多数语言不同,其中只有原语通过值传递,所有用户对象都通过引用自动传递。

话虽如此 - 例如 Qt 容器并没有真正复制实际的容器,除非您尝试修改它,这称为“复制或写入”,隐式共享以进行读取。

就您而言 - 如果BattleField4该类提供“深拷贝”构造函数或赋值运算符,那么这是可能的,但我怀疑任何头脑正常的人都会设计一个这样大小的游戏类。

游戏层次结构仍然存在,但它不会被限制在单个类实例中,它将成为多态层次结构的一部分。这意味着它将特别适合使用层次结构基类中存在并为每个特定对象实现的任何方法进行递归树遍历。这样的操作很可能不会在 RAM 内存中发生,但会将层次结构保存到磁盘 - 这就是保存和加载游戏进度的工作方式 - 所有游戏对象的整个状态都被序列化到磁盘以保存,并反序列化为恢复。当然,同样的技术也可以用于你所要求的,但这听起来并不明智。是的,在深拷贝的情况下,它会占用双倍的内存。如果您可以更改对象而不影响另一个对象,您将拥有两个单独的树。

于 2013-08-25T07:27:30.827 回答
0

C++ 中任何复杂类型的赋值都是用户定义的。标量和简单的聚合分配是按值分配的,但是一旦一个对象开始与对等点和依赖项建立关系,您就会准确地告诉 C++ 哪些部分需要真正的复制以及复制会产生哪些其他影响。您游戏的顶级媒体对象清单几乎肯定是一个简单的参考副本。

于 2013-08-25T13:44:30.260 回答
0

我自己回答我的问题:

复制对象的每个属性都会被复制。是的,这可能是一个性能问题。这就是人们使用指针的原因。使用“=”运算符时,C++ 会创建对象的“浅拷贝”(默认情况下)。可以定义一个复制构造函数来改变这一点,例如创建一个具有“深度复制”模式的类。

搜索什么是“浅拷贝”给了我想要的关于 C++ 对象拷贝如何工作的信息。

“浅拷贝”与“深拷贝”之间的比较非常有用:

对于包含指向其他对象的指针的对象,浅拷贝只复制指针而不复制它们指向的对象。结果是两个对象指向同一个包含的对象。深拷贝复制指针和它们指向的对象,以及包含在该对象中的任何指针或对象,等等。如果您只需要浅拷贝,请避免执行深拷贝。

于 2013-08-25T22:02:51.737 回答