如何将pythonic double for循环转换为标准代码?

时间:2018-09-25 13:30:24

标签: python for-loop

我遇到了这段难以理解的pythonic代码:

paths = [[end]]
while paths and paths[0][0] != start:
    paths = [[parent] + path for path in paths for parent in childToParents[path[0]]]

其中childToParents是:

defaultdict(<class 'set'>, {'cog': {'log', 'dog'},
                            'dog': {'dot'},
                            'dot': {'hot'},
                            'hit': None,
                            'hot': {'hit'},
                            'log': {'lot'},
                            'lot': {'hot'}})

end"cog",开始是"hit"。路径的预期输出为:

[["hit","hot","lot","log","cog"],["hit","hot","dot","dog","cog"]]

我尝试了双for循环的多种变体。一种这样的尝试是:

    paths=[[end]]
    while paths and paths[0][0] != start:
        for i in xrange(len(paths)):
            for parent in childToParents[paths[i][0]]:
                paths[i] = [parent] + paths[i]

但这只会给我:

[["hit","hot","dot","dog","log","cog"]]

如何将代码转换为标准的双for循环?

1 个答案:

答案 0 :(得分:1)

理解中的嵌套for循环从左到右起作用,因此最右边的循环是 inner 循环,左边的循环是 outer 。例如-

a = [1,2,3]
b = [8,9,0]

[(a1, b1) for a1 in a for b1 in b]

等效于:

l = []
for a1 in a:
    for b1 in b:
      l.append((a1, b1))
l

如果运行,两者都会输出以下内容

[(1, 8), (1, 9), (1, 0), (2, 8), (2, 9), (2, 0), (3, 8), (3, 9), (3, 0)]

对于您的示例代码-

paths = [[end]]
while paths and paths[0][0] != start:
    paths = [[parent] + path for path in paths for parent in childToParents[path[0]]]

相当于:

paths = [[end]]
while paths and paths[0][0] != start:
    paths_, paths = paths, []
    for path in paths_:
        for parent in childToParents[path[0]]:
            paths.append([parent] + path)
paths

请注意,paths_, paths = paths, []保留paths的内容以进行迭代,同时仍将其重置为后续循环。用您的输入运行上面的命令给我:

[['hit', 'hot', 'dot', 'dog', 'cog'], ['hit', 'hot', 'lot', 'log', 'cog']]