gpt4 book ai didi

python - numpy 向量化并行更新

转载 作者:太空宇宙 更新时间:2023-11-04 08:08:31 25 4
gpt4 key购买 nike

我想用以下简单规则实现一维元胞自动机:

  1. 如果单元格为1且相邻单元格为0,则(向右)移动
  2. 如果单元格为1且相邻单元格为1,则不要移动
  3. 所有细胞根据它们的状态同时更新。
  4. 我们有封闭边界条件。这意味着最后一个单元格的邻居是第一个单元格。

例如:

0 1 1 0 1

更新后:

1 1 0 1 0

我的解决方案是

def update(cells):
neighbors = np.roll(cells,-1)
dim = len(cells)
tmp_cells = np.zeros(dim)
for i,j in enumerate(cells):
if j and not neighbors[i]:
tmp_cells[i], tmp_cells[(i+1)%dim] = 0, 1
elif j:
tmp_cells[i] = 1
return tmp_cells

这很好,但解决方案并没有利用 np.arrays 的所有可能性,而是简化为一个简单的 list 算法。

我以为我可以在 cellsneighbors 之间找到一个简洁的逻辑,但显然我现在必须去 sleep 了。

一些想法?

最佳答案

要在不循环的情况下获取单元格的值,您需要知道它在两边 的邻居。您需要左边,因为如果您是 0,您的新值取决于您左边邻居的值,而如果您是 1,您的新值取决于您右边邻居的值。

你可以穷尽所有的 3 格组合,对吧?换句话说:

000 -> 0
001 -> 0
010 -> 0 # move to the right
011 -> 1 # stay put
100 -> 1 # left neighbor has moved
101 -> 1 # left neighbor has moved
110 -> 0 # move to the right
111 -> 1 # stay put

您可以很容易地将那个表变成一个 bool 函数。我们可以简化它,但让我们开始时是愚蠢的:-x & y & z | x & -y & -z | x & -y & z | x & y & z.

就是这样:

left = np.roll(cells, -1)
right = np.roll(cells, 1)
return (np.logical_not(left) & cells & right | # ...)

现在您当然想要简化 bool 方程,*但这应该让您入门。

* 或者退后一步,重新考虑规则。如果你是 0,你的新值总是从你左边的邻居那里复制;如果你是 1,它总是从你右边的邻居那里复制的。您可以使用 bool 运算符的组合来编写它,但使用掩码赋值可能会更简单:result[cells] = left[cells];结果[notcells] = right[notcells].

关于python - numpy 向量化并行更新,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27239173/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com