【问题标题】:Taking 'snapshots' of big Objects拍摄大物体的“快照”
【发布时间】:2015-02-17 20:25:38
【问题描述】:

我正面临以下问题。一个线程正在构建和更新树对象。要验证树,需要计算该树的哈希。所以第二个线程连续计算那棵树的哈希值。

现在我遇到了以下问题:那棵树的大小约为 300mb,我想确保树在计算哈希时不会改变,比如拍摄快照并计算它的哈希。

我的猜测是我有以下两种选择:

  1. 在计算哈希时阻止写入树。 (不理想,因为计算需要相当长的时间)
  2. 通过复制该对象来拍摄“快照”。然后计算哈希。 (也不是很好,因为需要另外 300mb 的内存)

是否有一种常见的技巧或模式可以对大对象进行“快照”而不只是复制它们?

(我的猜测是这需要对树对象进行深刻的更改,但我很感激每一个提示。)

提前致谢, fxh

PS:我不知道这个问题是否重要,但我使用的是 Java (1.8)

【问题讨论】:

  • 为什么不让哈希值始终保持新鲜?以一种廉价的方式逐步计算每个操作。
  • Scala 和 Clojure 具有不可变的数据结构。您可以使用不可变树(当您添加或删除节点时,它会返回一棵新树,该树引用旧树并共享大部分内存)。这是一个深刻的变化,但您可以使用他们现有的集合。最好的解决方案是@Magnamag,然后是不可变数据结构或在计算哈希时阻塞写入。
  • @flxh 请参阅此问题stackoverflow.com/questions/12324725/… 了解增量哈希定义和论文链接。

标签: java oop hash concurrency tree


【解决方案1】:

我认为您在计算新哈希时既不应该阻塞也不应该对整个树进行复制或拍摄快照,尤其是在树占用大约 300 mb 内存的情况下。

相反,我会采取另一种方法。我会使用增量哈希函数。我不是这些问题的专家,但到目前为止我所知道的最好的是来自greenrobot common 实用程序库的 Murmur3F。请检查他们的样品。

Murmur3F 让你可以多次调用它的update() 方法。然后调用getValue() 来获取实际的哈希值。你可以多次这样做。 因此,每次修改它时,我都不会在单独的线程中重新计算整个树的哈希值。例如,使用该 Murmur3F 哈希实现,我会在每次更新树时使用 update() 方法,并在树的 getHash() 上使用 getValue()。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2013-02-14
    • 1970-01-01
    • 1970-01-01
    • 2014-12-03
    • 1970-01-01
    • 2018-12-03
    • 1970-01-01
    相关资源
    最近更新 更多