如何通过 python 中的子文件夹遍历文件夹

how iterate through a folder by subfolder in python

我有一个文件夹,里面装满了数千个 .ai 文件。这个文件夹的排列方式是它最初有以客户名称命名的子文件夹,并且在每个子文件夹中都有一个唯一的目录,其中包含一些或许多包含 .ai 的子文件夹,或者 subs... 中包含 .ai 的子文件夹中的子文件夹, 或者没有子文件夹只有 .ai 文件。

我需要一个程序,它将通过获取客户子文件夹内的每个 .ai 文件名(无论有多少子文件夹,或子文件夹中的子文件夹等...)来遍历此文件夹,并将其附加到列表中。然后我将获取该列表并稍后对其进行一些 ocr 处理,但完成后我将清除该列表并移至下一个子文件夹。

这是我用来尝试此操作但失败的代码。它 return 有时是一个空列表,或者是一个只有一个文件名的列表,而它应该 return 每次都是一个列表,其中包含一个或多个 .ai 文件名。

def folder_loop(folder):
    temp_list = []
    for root, dirs, files in os.walk(folder):
        for dir in dirs:
            for file in dir:
                if file.endswith("ai"):
                    temp_list.append(os.path.join(root, file))
        print(temp_list)
        temp_list.clear()

我是初学者,我几乎不明白代码在做什么,所以我对它不起作用并不感到惊讶。有什么想法吗?

有一个社区 post here 有一些非常完整的答案。

也就是说,我的个人实用程序工具箱中有以下方法。

def get_files_from_path(path: str=".", ext=None) -> list:
    """Find files in path and return them as a list.
    Gets all files in folders and subfolders

    See the answer on the link below for a ridiculously
    complete answer for this.
    
    Args:
        path (str, optional): Which path to start on.
                              Defaults to '.'.
        ext (str/list, optional): Optional file extention.
                                  Defaults to None.

    Returns:
        list: list of full file paths
    """
    result = []
    for subdir, dirs, files in os.walk(path):
        for fname in files:
            filepath = f"{subdir}{os.sep}{fname}"
            if ext == None:
                result.append(filepath)
            elif type(ext) == str and fname.lower().endswith(ext.lower()):
                result.append(filepath)
            elif type(ext) == list:
                for item in ext:
                    if fname.lower().endswith(item.lower()):
                        result.append(filepath)
    return result

您可以尝试以下方法:

如果您想为函数提供 base 文件夹,其中包含所有客户文件夹,然后需要每个客户文件夹的所有 .ai-文件(来自每个子级别):

from pathlib import Path

def folder_loop(folder):
    for path in Path(folder).iterdir():
        if path.is_dir():
            yield list(path.rglob("*.ai"))

Path.rglob("*.ai") is recursively globbing 给定的 Path 及其 .ai 文件的所有子文件夹。

要使用它:

the_folder = "..."
for file_list in folder_loop(the_folder):
    print(file_list)
    # do whatever you want to do with the files

如果您想给它一个文件夹并想要一个包含所有 .ai 文件的列表:

def folder_loop(folder):
    return list(Path(folder).rglob("*.ai"))

此处的 yielded/returned 列表包含 Path-对象(非常方便)。如果你想要字符串,那么你可以做

       ....
            yield list(map(str, path.rglob("*.ai")))

等等