我有一种我会问一个“愚蠢”的问题,但我必须问...

我有2台虚拟机。

我想将一个对象的实例从一个对象复制到另一个,

是否可以复制代表该对象在VM堆中的位,将其发送到另一个VM,例如另一个VM只需要在内存中分配位置并在此内存插槽中添加引用。 。

目前,为了做这样的事情,我们将对象序列化并取消序列化,这效率要低得多(计算明智),而不是复制实例……解析是计算浪费...

JS序列化示例:每个VM是 V8 (JavaScript),一种方法是将对象转换为JSON(JSON.stringify),将其发送一些方法,以获取字符串并将其转换回对象的其他VM(例如 var myObject = eval('(' + myJSONtext + ')');)..(JavaScript只是一个示例,这是某种序列化)

有帮助吗?

解决方案

让我们忽略一秒钟的天真假设,您可以轻松地将此问题推广到多个VM上。任何建立这样的机制的尝试都将在很大程度上取决于您要构建的VM的实施细节。

以下是没有这样做的几个原因:

  1. 核心内表示通常不可移植在架构之间。如果我在不了解其结构的情况下将SPARC机上VM的“对象”发送到X86计算机上的VM,则该对象在另一侧会损坏。

  2. 该对象不会在两台机器上的同一内存位置上都存在,因此对象内的内部指针在到达第二个VM后需要修补。这也需要内部了解对象的结构。

  3. 该对象可能包含对其他对象的引用,因此复制对象意味着复制对象树,通常也不是无环树。您最终建立了看起来很糟糕的序列化库的代码,以可靠地执行此操作。

  4. 对象通常保留无法可靠地传输机器的本机资源(例如文件手柄和套接字)。

  5. 在许多VM中,在数据(您要复制的对象)和元数据(例如,您要复制的对象类)之间有一个区别。在这些类型的VM中,即使您可以毫发无损地复制对象位,也可能取决于一堆在遥控端不存在的元数据。复制元数据位比位也很棘手,因为许多VM都使用实现技术(例如,实现的字符串或内存映射的对象代码)使数据本质上不可存储。您可能还会获得比您想要的要多得多(例如,.NET是最小的元数据单元,您可以包装并发送某个地方通常是一个组件)。

  6. 在同一VM的不同版本中,内部内表示不可移植,也不包含可用于修补数据的内部版本信息。

  7. 内部核心表示包含许多不需要复制的内容(例如内联缓存,垃圾收集信息)。复制这些东西将是浪费的,并且信息在另一侧甚至可能不明智。

基本上,为了可靠地执行此操作,您最终会构建世界上最尴尬和最不可靠的序列化库,并且简单记忆副本的性能提升在修补了许多副本时会弄清许多东西时,丢失了。

因此,这些机制往往不存在。

该规则有一个巨大的例外:基于图像的虚拟机(例如许多SmallTalk和Self VMS)是围绕一个可以复制,在机器之间移动的“图像”的想法。通常的性能成本很高。

其他提示

为什么不使用cpickle。它将非常可靠地序列化数据,然后您可以通过插座,名为Pipe,mmap,您将其命名,除非在另一端,只要您可以可靠地重新组装它,只要它不会在传输中损坏而且咸菜模块的版本并没有大不相同。当然,真正的企业方法是使用平台不可知的标准,例如XML,这将使您可以将平台互操作性扩展到Python之外。我知道这是一个问题,但是我认为为Python解释器代码库做出了贡献的人必须为您澄清一下。

我敢肯定,在VMware API中没有办法进行这种直接内存传输;我不知道其他虚拟机管理程序,但我仍然怀疑。 VMware具有将整个计算机的内存运送到另一台主机服务器的方法(主要是通过使用分页文件),但是没有什么能从运行程序中提取一块内存并将其提供给另一台内存 - 涉及太多的那里。

因此,您现有的对象序列化策略绝对是解决此需求的一个好的解决方案,幸运的是,您正在使用的编程语言有很好的选择(Python, 爪哇).

但是我想知道您是否真的需要将整个对象藏起来并重新创建,或者仅包括一些数据。如果数据不过多,您可以使用某种 远程方法调用 要将消息从源VM发送到接收器,告诉其使用此数据创建对象。在这种情况下,您将仅序列化所需的数据,并让目标计算机在其自身内存中重新构建对象。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top