0

我想使用 OpenGL 在 Python中模拟体心立方晶体结构。我已经编写了代码来获取next_nodes,如果节点满足边界则打印,否则递归查找下一个节点返回。

但是代码有一些问题,它无限运行。谁能帮我解决这个问题。在下面发布相关代码(删除了所有 OpenGL 调用)。

def get_node(x,y,z,side):
    return [x+side,y,z],[x,y+side,z],[x,y,z+side],[x-side,y,z],[x,y-side,z],[x,y,z-side]

def goto_next_nodes(x,y,z,cube_side,next_nodes,boundary_x,boundary_y,boundary_z):
    for node in next_nodes:
        if 0<=node[0]<=boundary_x and 0<=node[1]<=boundary_y and 0<=node[2]<=boundary_z:
             print node
             x,y,z=node[0],node[1],node[2]
             next_nodes=get_node(x,y,z,cube_side)
             goto_next_nodes(x,y,z,cube_side,next_nodes,boundary_x,boundary_y,boundary_z)
        else:
            return

def display_fcc(cube_side,boundary_x,boundary_y,boundary_z):
     x=y=z=0
     next_nodes=get_node(x,y,z,cube_side)
     goto_next_nodes(x,y,z,cube_side,next_nodes,boundary_x,boundary_y,boundary_z)

display_fcc(5,10,10,10)

递归始于display_fcc函数,goto_next_node是递归函数。

4

2 回答 2

4

您的next_node函数返回距离 一步之遥的所有节点,(x,y,z)然后goto_next_node您开始访问边界内的所有节点。但是当您访问一个节点时,您从不检查您之前是否访问过该节点。所以你的算法卡在一个角落里,一圈又一圈,一次又一次地访问一个节点循环。如果您查看输出,您可以清楚地看到这一点:

>>> display_fcc(5,10,10,10)
[5, 0, 0]
[10, 0, 0]
[5, 5, 0]
[10, 5, 0]
[5, 10, 0]
[10, 10, 0]
[5, 5, 5]
[10, 5, 5]
[5, 10, 5]
[10, 10, 5]
[5, 5, 10]
[10, 5, 10]
[5, 10, 10]
[10, 10, 10]
[0, 5, 5]  
[5, 5, 5]      # Oops: we've been here before!
[10, 5, 5]
[5, 10, 5]
[10, 10, 5]
[5, 5, 10]
[10, 5, 10]
[5, 10, 10]
[10, 10, 10]
[0, 5, 5]
[5, 5, 5]      # And around we go again.
...

所以你需要跟踪你去过的地方,并确保你不会再去那里。

于 2012-08-28T10:29:14.017 回答
4

你可以记住你看到的节点,不要第二次去那里,就像这段代码一样。但我认为你还需要解决一件事,

else:
    return

我认为这是不正确的,因为您的 for 将不再迭代。

def get_node(x, y, z, side):
    return [(x+side,y,z), (x,y+side,z), (x,y,z+side),
            (x-side,y,z), (x,y-side,z), (x,y,z-side)]

seen_nodes = set()

def goto_next_nodes(x, y, z, cube_side, next_nodes, boundary_x, boundary_y, boundary_z):
    for node in next_nodes:
        if node not in seen_nodes:
            seen_nodes.add(node)
            if 0<=node[0]<=boundary_x and 0<=node[1]<=boundary_y and 0<=node[2]<=boundary_z:
                 print node
                 x,y,z=node[0],node[1],node[2]
                 next_nodes=get_node(x,y,z,cube_side)
                 goto_next_nodes(x,y,z,cube_side,next_nodes,boundary_x,boundary_y,boundary_z)
    return

def display_fcc(cube_side,boundary_x,boundary_y,boundary_z):
     x=y=z=0
     next_nodes=get_node(x,y,z,cube_side)
     goto_next_nodes(x,y,z,cube_side,next_nodes,boundary_x,boundary_y,boundary_z)

display_fcc(5,10,10,10)
于 2012-08-28T10:33:27.817 回答