1

我有一个像下面这样的构造,如何使用 1 个(或更多)列表推导来获得相同的输出?

f2remove = []
for path in (a,b):
    for item in os.listdir(path):
        if os.path.isdir(os.path.join(path,item)):
            x = parse_name(item)
            if x and (ref - x).days >= 0:
                f2remove.append(os.path.join(path,item))

我尝试了多种方法,例如

files = [parse_name(item)\
         for item in os.listdir(path) \
         for path in (a,b)\
         if os.path.isdir(os.path.join(path,item))] # get name error
f2remove = [] # problem, don't have path...

错误:

Traceback (most recent call last):
  File "C:\Users\karuna\Desktop\test.py", line 33, in <module>
    for item in os.listdir(path) \
NameError: name 'path' is not defined
4

2 回答 2

4

s的顺序for不变。您的情况变得尴尬:

f2remove = [
    os.path.join(path, item)
    for path in (a,b)
        for item in os.listdir(path)
            if os.path.isdir(os.path.join(path, item))
               for x in (parse_name(item),)
                  if x and (ref - x).days >= 0
   ]

基本上,要将嵌套for的 s 转换为列表推导式,您只需将您正在append使用的任何内容移到前面:

result = []
for a in A:
    for b in B:
      if test(a, b):
         result.append((a, b))

变成

result = [
    (a, b)
    for a in A
    for b in B
    if test(a, b)
]
于 2013-03-11T18:14:47.490 回答
2

这应该做的工作,

f2remove = [
       os.path.join(path,item) 
            for item in [os.listdir(path)
                for path in (a,b)] 
                     if os.path.isdir(os.path.join(path,item)) 
                           and parse_name(item) and 
                                 (ref - parse_name(item)).days >= 0]

但是您的初始版本确实更具可读性。

于 2013-03-11T18:22:11.943 回答