我怎么能在列表推导中重写这个for循环

时间:2014-01-02 07:43:04

标签: python python-2.7 for-loop list-comprehension

我得到了一个像这样的“for循环”:

for dirctory in dirs:
    for item in os.walk(dirctory):
        for i in item[2]:
            i = os.path.join(item[0], i)
            if is_image(i):
                images.append(i)

我尝试将其重写为列表推导,我尝试了这个:

images.extend(filter(is_image, [item[0]+i for i in item[2] for item in os.walk(dirctory)]))

它表示UnboundLocalError:在赋值之前引用的局部变量'item'

所以我尝试了这个:

images.extend(filter(is_image, [(item[0]+i for i in item[2]) for item in os.walk(dirctory)]))

它说TypeError:强制转换为Unicode:需要字符串或缓冲区,找到生成器

我在OS X中使用Python 2.7.4。

3 个答案:

答案 0 :(得分:1)

试试这个:

[os.path.join(item[0], i) for directory in dirs for item in os.walk(dirctory) for i in item[2] if is_image(os.path.join(item[0], i))]

答案 1 :(得分:1)

def check_image(directory, file_name):
    file_name = os.path.join(directory, file_name)
    return is_image(file_name), file_name

[full_path
     for current_dir in dirs
     for parent_dir, _, files in os.walk(current_dir)
     for current_file in files
     for isimage, full_path in [check_image(parent_dir, current_file)]
         if isimage]

check_image功能可以避免两次应用os.path.join

答案 2 :(得分:0)

以下是如何做到的(这不是我测试的)

[os.path.join(path+fname)  for path, _, files in os.walk('some_folder') 
 for fname in files if os.image(os.path.join([path,fname]))]

但是 - 如果你注意 - 你必须在这个解决方案中加入路径两次,所以直接的嵌套循环可能更有效

修改

在我的示例中,我通过扩展名查找Python文件,因此在这种情况下,列表理解不会受到路径/文件名双重连接的影响