【问题标题】:How to stop iteration when if statement is true?if语句为真时如何停止迭代?
【发布时间】:2011-04-02 00:10:35
【问题描述】:

我在 Python 中停止迭代时遇到了一些麻烦。这个问题出现在函数中:

for z in range(w.steps):
    for i in range(1,w.x-1):
        for j in range(1,w.y-1):
            print (i, j)
            for r in data.c:
                if w.world[i][j] in r:
                    print r
                    ind = data.c.index(r)
                    print ind
                    if w.world[i-1][j] in data.n[ind]:
                        if w.world[i][j+1] in data.e[ind]:
                            if w.world[i+1][j] in data.s[ind]:
                                if w.world[i][j-1] in data.w[ind]:
                                    w.world[i][j] = data.cc[ind]

步数(第一个 for 循环)由用户提供。接下来的两个for循环用于遍历二维数组(x-rows,y-cols):

for i in range(1,w.x-1):
    for j in range(1,w.y-1):

(打印仅用于控制) 对于数组中的每个单元格,我想检查它的值。我在 data.c 列表中有所有可能的值(比如说 value=14),看起来像这样:

li = [[2],[14,23],[4]]

所以指令:

for r in data.c:
    if w.world[i][j] in r:

我想在第一个 true 出现时停止迭代。如果函数将达到第一个相等的值,我想分配包含它的列表的索引,并执行其他语句:

ind = data.c.index(r)
    if w.world[i-1][j] in data.n[ind]:
        if w.world[i][j+1] in data.e[ind]:
            if w.world[i+1][j] in data.s[ind]:
                if w.world[i][j-1] in data.w[ind]:
                    w.world[i][j] = data.cc[ind]

如果它们都是true,我想执行最后一条指令(赋值),然后从数组中转到下一个单元格。但如果其中至少有一个是false,我想回去,并在data.c 列表中寻找下一个命中(可能不止一个)。列表中肯定有所有可能性的值。关键是先使用哪个会匹配。

我为 1 个单元格尝试了此功能,但我得到的索引比预期的要多,我不知道为什么。使用我的 cmets 从数组中输出一个单元格:

(1, 1)     # print(i,j)
[0]        # print r
3          # print data.c.index(r)
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3
[0]
3

我将非常感谢任何帮助,因为我处理这个算法很长时间了(我是编程初学者)。

【问题讨论】:

  • 一个好的经验法则:如果您需要 9 级缩进,请考虑重构您的代码。
  • 我真的建议你找一些 Python 书(真的 - 任何书)并阅读它。通读所有内容。在不知道一半语法结构的情况下通过示例学习可能真的很痛苦。而且真的毫无意义。这就是我被介绍给我的第一语言 - 帕斯卡的方式,我想我浪费了很多时间。
  • 感谢所有建议,我将重构我的代码。我知道最好的方法是先通读整本书,但事实是我们有一些课程要完成,有时很遗憾没有时间通读所有内容。

标签: python iteration


【解决方案1】:

如果我理解正确,你需要放置一个break 声明。

for z in range(w.steps):
    for i in range(1,w.x-1):
        for j in range(1,w.y-1):
            print (i, j)
            for r in data.c:
                if w.world[i][j] in r:
                    print r
                    ind = data.c.index(r)
                    print ind
                    if w.world[i-1][j] in data.n[ind]:
                        if w.world[i][j+1] in data.e[ind]:
                            if w.world[i+1][j] in data.s[ind]:
                                if w.world[i][j-1] in data.w[ind]:
                                    w.world[i][j] = data.cc[ind]
                                    break # <-- break "for r" and continue with "for j"

【讨论】:

  • 它的作用与下面评论中描述的相同。
  • @Mateusz:用少量数据样本在论文上逐步检查您的算法。算法可能存在逻辑错误。
【解决方案2】:
    for (z,i,j) in itertools.product(range(w.steps), range(1,w.x-1)), range(1,w.y-1)):
        for r in data.c:
            if w.world[i][j] in r :
                ind = data.c.index(r)
                if all (itertools.imap(lambda x, y: x in y, 
                                    (w.world[i-1][j], w.world[i][j+1],w.world[i+1][j], w.world[i][j-1]), 
                                    (data.n[ind], data.e[ind], data.s[ind], data.w[ind]))):
                    w.world[i][j] = data.cc[ind]
                    break

【讨论】:

  • 我尝试使用您的代码,但是当我在第一个 if 语句之后放置 print(i,j)print r 以及 print ind 时,我收到了与一个相同的输出从问题(上)。即使其他if 语句是错误的(甚至其中之一),它也应该检查data.c 中的下一个语句,因此索引应该不同。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-07-01
  • 1970-01-01
  • 2012-09-30
相关资源
最近更新 更多