【问题标题】:Optimising conways game of life优化康威人生游戏
【发布时间】:2013-09-13 19:26:33
【问题描述】:

我正忙于编码Conways Game of Life,我正在尝试使用一些数据结构来优化它,该结构记录在每个生命周期中应该检查哪些单元格。

我使用 arrayList 作为动态数据结构来记录所有活细胞及其邻居。有没有更好的数据结构或保留更短列表的方法来提高游戏速度?

我问这个是因为经常检查许多单元格但没有更改,所以我觉得我的实现可以改进。

【问题讨论】:

  • 对于不熟悉的人,添加“康威人生游戏”的链接可能会有所帮助,或者至少很有趣。
  • 几年前我见过一个使用 LinkedList 的实现,速度非常快,但遗憾的是我没有详细信息。它在一本老 Sam 的编程书中。
  • 我认为具有 4 个指向其他节点的指针的节点可能非常快
  • 无论你做什么,give this a try。超越大多数人的做法,即盲目尝试并希望最好。
  • 您可以使用 BitSet 标记活细胞,这将允许您一次跳过 64 个不活动的细胞。您可以向单元格添加前向和后向链接,并避免辅助列表的开销。您可以使用 Hashlife 的思想而忘记低级优化。

标签: java performance data-structures


【解决方案1】:

我相信Hashlife algorithm 可以帮到你。

它给出了使用quadtree(每个内部节点恰好有四个子节点的树数据结构)来保存数据的想法,然后它使用哈希表来存储四叉树的节点。

为了进一步阅读,this post,由 Eric Burnett 编写,对 Hashlife 的工作原理、性能和实现(尽管使用 Python)提供了深刻的见解。值得一读。

【讨论】:

  • 为什么需要哈希表来存储叶子?四叉树可以完美地实现为“树”,不需要散列。
  • @IraBaxter 遍历哈希表比遍历树更容易。这太有趣了,我确实想到了同样的事情!我没有意识到它有一个实际的数据结构和算法。
  • @progenhard:不。关键是你可以缓存整个子树的结果,这是一个巨大的收获。
  • 我认为四键和怪物曲线更快,并且还可以降低空间质量。
  • @Ira Baxter:不,这些数字来自the web,并且(某种程度上)反驳了你的说法。在Dr. Dobb's 中有一个很好的解释它是如何工作的。
【解决方案2】:

早在 1970 年代,我就使用 2Mhz 6800 8 位计算机构建了一个 Life 引擎,该引擎在直接映射到屏幕像素的 256x512 位网格上运行。我直接在显示像素上进行(它们是一位开/关白/黑),因为我想查看结果并且没有看到将 Life 图像复制到显示器的意义。

它的基本技巧是将问题视为根据生命规则评估“此单元格已打开”的布尔逻辑公式之一,而不是像往常一样计算活着的邻居。这个公式很容易弄清楚,所以留作家庭作业。让它快速的原因是布尔公式是按位计算的,一次计算 8 位。如果您扫过屏幕并跨行扫描,您实际上可以一次评估 N 位(6800 上为 8,现代 PC 上为 64),开销非常低。如果您发疯了,您可能会使用 SIMD 向量扩展并“一次”执行 256 位或更多位。最重要的是使用 GPU 来执行此操作。

6800 版本将在大约 0.5 秒内处理一个完整的屏幕;您可以在屏幕上从上到下观看更新涟漪(60 Hz 刷新)。在具有 1000 倍时钟频率(1 GHz 很容易获得)和一次 64 位的现代 CPU 上,它应该能够每秒产生数千帧。如此之快,你无法看到它运行:-{

一个有用的观察是生命世界的大部分是死的(空白),处理这部分主要会产生更多的死细胞。这建议使用稀疏表示。另一张海报建议使用四叉树,我认为这是一个非常好的建议。您的四叉树区域也不必是方形的。

结合这两个想法,非空白区域的四叉树与四叉树指定的位块的位级处理可能会给出一个惊人的快速生命算法。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2010-09-07
    • 2012-01-19
    • 1970-01-01
    • 2018-01-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-02-21
    相关资源
    最近更新 更多