【问题标题】:how can I get my game of life code to animate correctly? (written in python)我怎样才能让我的生命代码游戏正确动画? (用python编写)
【发布时间】:2020-05-15 13:40:11
【问题描述】:

对于我自己的自我开发项目,我正在用 Python 创建 John Conway 的生活游戏,但我遇到了一个问题。我的代码正在编译,没有错误,但是在执行时它的运行与我期望的不同。我的代码如下:

from tkinter import *
from random import *
import time
import copy

PIXEL_SIZE = 10
ROW = 910
COLUMN = 700
#updated_grid = [[]]

def create_grid(r, c):
    grid = []
    for row in range(0, r):
        grid2 = []
        for column in range(0, c):
            grid2.append(randint(0, 1))
        grid.append(grid2)
    return grid


grid = create_grid(ROW, COLUMN)
updated_grid = create_grid(ROW, COLUMN)


def draw_grid():
    for row in range(0, ROW):
        for column in range(0, COLUMN):
            if grid[row][column] == 1:
                x0 = row*PIXEL_SIZE
                y0 = column*PIXEL_SIZE
                x1 = x0+PIXEL_SIZE
                y1 = y0+PIXEL_SIZE
                canvas.create_rectangle(x0, y0, x1, y1, fill='red')


def apply_rules():
    for row in range(1, ROW - 1):
        for column in range(1, COLUMN - 1):
            neighbours_count = 0
            # will count the neighbours for each cell
            neighbours_count += grid[row-1][column-1] # top left
            neighbours_count += grid[row][column-1] # top center
            neighbours_count += grid[row+1][column-1] # top right

            neighbours_count += grid[row-1][column] # middle left
            neighbours_count += grid[row+1][column] # middle right

            neighbours_count += grid[row-1][column+1] # bottom left
            neighbours_count += grid[row][column+1] # bottom center
            neighbours_count += grid[row+1][column+1] # bottom right

            # Game Of Life rules:

            # alive cell rules
            if grid[row][column] == 1:
                if neighbours_count < 2: # rule 1 any live cell with fewer than two live neighbours dies, as if by underpopulation
                    updated_grid[row][column] = 0
                elif neighbours_count == 2 | neighbours_count == 3: # rule 2 any live cell with two or three live neighbours lives on to the next generation
                    updated_grid[row][column] = 1
                elif neighbours_count > 3 & neighbours_count <= 8: # rule 3 any live cell with more than three live neighbours dies, as if by overpopulation
                    updated_grid[row][column] = 0
                else:
                    updated_grid[row][column] = 0
            elif grid[row][column] == 0: # dead cells rule 4 any dead cell with exactly three live neighbours becomes a live cell, as if by reproduction
                if neighbours_count == 3:
                    updated_grid[row][column] = 1
                else:
                    updated_grid[row][column] = 0
    for row in range(0, ROW):
        for column in range(0, COLUMN):
            grid[row][column] = updated_grid[row][column]


def one_cycle():
    apply_rules()
    draw_grid()
    window.after(1, one_cycle)


window = Tk() # creates the window for the game
window.title('Game Of Life Python') # is the game title written on the window
canvas_frame = Frame(window) # creates a frame on the window to hold the canvas
game_title = Frame(window) # creates a frame on the window to display the game title (which will be a label)
start_button = Button(window, text='Start Game', command=one_cycle) # creates a button which will be used to start the game
canvas = Canvas(canvas_frame, width=ROW, height=COLUMN, background='black') # creates the canvas used to the draw the game of life
game_title_label = Label(game_title, text='Game Of Life', font='Helvetica 20 bold', fg='grey') # creates the label for the game title which will be placed in a frame

canvas.grid(row=0, column=0) # places the canvas onto the canvas_frame
canvas_frame.grid(row=1, column=1) # places the canvas_frame onto the window
game_title_label.grid(rowspan=2, column=0) # places the title of the game onto the game_title frame
game_title.grid(row=0, columnspan=2) # places the frame for the game title onto the window
start_button.grid(rowspan=2, column=1) # places the start onto the window

window.mainloop()

通过查看代码,我只能认为错误出在 appy_rules() 方法的某个地方(我可能错了),但我仍然无法弄清楚为什么动画没有被重绘,而是在彼此之上绘制.我是 python 新手,因此非常感谢您提供的任何帮助,再次感谢您。

【问题讨论】:

  • 请更新您的问题,准确描述问题。 running incorrectly 不是很精确。

标签: python python-3.x animation canvas tkinter


【解决方案1】:

我看到了两件主要的事情:

您创建的矩形数量是您需要的 100 倍,这就是为什么它可能会感觉很慢。与:

PIXEL_SIZE = 10
ROW = 91          # One tenth of original value
COLUMN = 70       # One tenth of original value

您可以将画布创建为:

canvas = Canvas(canvas_frame, width=PIXEL_SIZE*ROW,
                height=PIXEL_SIZE*COLUMN, background='black')

然后像以前一样使用 ROW & COLUMN。否则,您将为每个draw_grid() 在画布上创建 910*700 矩形。

然后,您在绘制时不会从画布中删除之前的矩形。只需在draw_grid() 中添加删除语句:

def draw_grid():
    canvas.delete('all')
    # rest of code...

我尚未检查您的规则是否按预期工作,但这应该是一个开始。

【讨论】:

  • 感谢动画重绘的帮助,而不是在已经存在的内容之上绘制单元格,并且速度更快。但有些地方仍然不太对劲,它似乎运行得太快了。
  • after() 函数以毫秒为单位工作,因此您在重绘网格一毫秒后开始一个新的循环。根据自己的喜好调整。
【解决方案2】:

抱歉,我之前修复您的代码时应该记住这一点。其实你对规则的执行不太对:

            # Game Of Life rules:

            # alive cell rules
            if grid[row][column] == 1:
                if neighbours_count < 2:
                    updated_grid[row][column] = 0
                elif neighbours_count == 2 or neighbours_count == 3: # rule 2 needs OR
                    updated_grid[row][column] = 1
                elif neighbours_count > 3 and neighbours_count <= 8: # rule 3 needs AND
                    updated_grid[row][column] = 0
                else:
                    updated_grid[row][column] = 0
            else: # dead cells rule 4 (can be done with else:)
                if neighbours_count == 3:
                    updated_grid[row][column] = 1

您使用了二进制或 (|) 和二进制与 (&amp;) 而不是逻辑版本。

【讨论】:

  • 我必须查找何时使用逻辑和二进制或/和感谢的差异
  • 似乎有很多东西here
【解决方案3】:

一般来说,一个好的做法是在整个代码中放置一堆测试打印函数,这样您就可以通过查看最后打印的字符串来了解代码失败的地方。编写这些字符串是为了描述代码刚刚所做的事情。尝试在您认为代码失败的地方执行此操作。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-05-14
    • 2020-08-28
    • 2022-11-07
    • 1970-01-01
    • 2023-01-21
    • 1970-01-01
    • 2012-12-24
    相关资源
    最近更新 更多