繁体   English   中英

康威的人生游戏:如何初始化网格?

[英]Conway's game of life: How to initialize the grid?

我正在尝试编写一个函数nextGen ,该函数接受单个参数(当前网格),然后计算但不打印新网格。 基本上,我不确定如何执行检查位,它会检查周围的9个单元格。 首先,我以为我可以创建一个完全由0构成的基本网格,该网格比当前网格大2行2列,因此它是0的边界,但是我不知道如何获取初始网格的值进入基础网格。 我当前的代码是:

def initlist(positions,initval):
    newlist = []
    for i in range(0,positions):
        newlist.append(initval)
    return newlist

def init2DTableV3(rows,cols,initval):
    newrow = initlist(cols,initval)
    table = initlist(rows,newrow)
    return table

def nextGen(current_grid):
    rows = len(current_grid)
    cols = len(current_grid[0])
    base_value = 0
    base_grid = init2DTableV3(rows + 2, cols + 2, base_value)
    import copy
    init_newgrid = copy.deepcopy(current_grid)

有人可以帮我吗? 我是Python的初学者,所以如果有人可以解释如何使用基本的Python函数来制作nextGen ,那就太好了。

如果我理解正确,则说明您具有基本网格,并且不确定如何在边缘上填充零,对吗?

有时,首先考虑一维问题比较容易,然后查看是否有可能将其扩展到2D。 假设您的1D网格看起来像

1 0 0 1 0 0 0 0 1 0 1

然后,如果您想在数组的两端都填充零,则它看起来像

0 1 0 0 1 0 0 0 0 1 0 1 0

假设您只是使用标准的Python列表,这很容易做到。 您可以简单地使用list.insert()插入开头,并使用.insert().append()插入结尾。

>>> L = [1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 1]
>>> L.insert(0,0)
>>> L.append(0)
>>> L
[0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 1, 0]

因此,让我们用2D列表尝试相同的事情,看看会发生什么:

>>> M = [[1,1],[1,1]]
>>> M.insert(0,[0,0])
>>> M.append([0,0])
>>> M
[[0, 0], [1, 1], [1, 1], [0, 0]]

因此,这在顶部和底部给出了一个带有零的行,但是我们没有左侧和右侧。 我们将在稍后处理。 当我添加顶行和底行时,我明确为其指定了所需的零个数(即[0,0] )。 但是您可以轻松地自动执行此操作,只需使用一行的长度即可:

>>> M = [[1,1],[1,1]]
>>> M.insert(0,[0]*len(M[0]))
>>> M.append([0]*len(M[0]))
>>> M
[[0, 0], [1, 1], [1, 1], [0, 0]]

现在,每个行向量的长度仅为2,但应为4。一个简单而明确的方法是遍历子列表并插入并附加0:

>>> for r in M:
...     r.insert(0,0)
...     r.append(0)
... 
>>> M
[[0, 0, 0, 0], [0, 1, 1, 0], [0, 1, 1, 0], [0, 0, 0, 0]]

这将为您提供填充的2D列表。


但是总的来说,我建议对这些任务使用numpy ,因为您可以简单地在2D numpy数组上使用numpy.pad()作为启动器,但是更复杂的操作也将更快,并且数组更易于索引等。

另一种方法是使用已经存在的内容,而不是添加额外的元素。

我最近用javascript写了Life的副本,但是想法是一样的。 每个单元格均由其坐标标识,并使用其邻居坐标的对象(Python:字典)进行初始化。

makeCell(x, y) {
    let div = $('<div></div>');
    let id = "x" + x + "y" + y;

    let neighbors = this.getNeighbors(x, y);

    let attributes = {
                "id": id,
                "data-entity": _entity.id
        }

    $("#grid").append(div);
}

function getNeighbors(x, y) {
    let leftX =     x - 1;
    let rightX =    x + 1;
    let topY =      y - 1;
    let bottomY =   y + 1;

    // neighbor positions
    let neighbors = [
        "#x" + leftX + "y" + topY,
        "#x" + x + "y" + topY,
        "#x" + rightX + "y" + topY,
        "#x" + leftX + "y" + y,
        "#x" + rightX + "y" + y,
        "#x" + leftX + "y" + bottomY,
        "#x" + x + "y" + bottomY,
        "#x" + rightX + "y" + bottomY,
    ];
    return neighbors;
}

在该回合结束时,所有活细胞都存储在列表中。 检查每个活细胞及其每个邻居,以计算其各自的活邻居细胞。

this.cellCountNeighbors = function() {
    let count = 0;
    let neighbors = this.neighbors;
    let n = this.entity;
    let u = this;

    neighbors.forEach(function(neighbor) {
        let div = $(neighbor);
        if ($(div).hasClass("alive")) {
            count++;
        } else if (!check_cells.includes(neighbor)) {
            check_cells.push(neighbor);
        }
    });

    return count;
}

以及生活检查条件:

this.setNextLife = function(_count) {
    if (this.alive) {

        if (_count == 2 || _count == 3) {
            return this.age++;
        } else {
            changes.push(this);
            return;
        }

    } else {
        changes.push(this);
    }
}

其中changes是小区的名单被切换bool活着/死亡。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM