Получение списка всех подкаталогов в текущем каталоге

Есть ли способ вернуть список всех подкаталогов в текущем каталоге в Python?

Я знаю, что вы можете делать это с файлами, но вместо этого мне нужно получить список каталогов.


person Brad Zeis    schedule 10.06.2009    source источник
comment
Если вы ищете решение pathlib, сделайте [f for f in data_path.iterdir() if f.is_dir()] кредит: stackoverflow.com/a/44228436/1601580. это дает вам имена папок в виде строк. Как-то также исключает . и .. слава богу. Решение Glob тоже стоит того: glob.glob("/path/to/directory/*/").   -  person Charlie Parker    schedule 20.07.2020


Ответы (30)


Вы имеете в виду непосредственные подкаталоги или каждый каталог прямо в дереве?

В любом случае для этого можно использовать os.walk:

os.walk(directory)

даст кортеж для каждого подкаталога. Первая запись в 3-кортеже - это имя каталога, поэтому

[x[0] for x in os.walk(directory)]

должен рекурсивно предоставить вам все подкаталоги.

Обратите внимание, что вторая запись в кортеже - это список дочерних каталогов записи в первой позиции, поэтому вы можете использовать это вместо этого, но это вряд ли вас сильно сэкономит.

Однако вы можете использовать его только для непосредственного предоставления дочерних каталогов:

next(os.walk('.'))[1]

Или просмотрите другие уже опубликованные решения, используя os.listdir и _ 6_, в том числе на "Как получить все непосредственные подкаталоги в Python ".

person Blair Conrad    schedule 10.06.2009
comment
Такой чистый и приятный ответ. Спасибо. Я не был знаком с next () и подумал, что эта ссылка может быть полезна тем, кто попал в аналогичную ситуацию: stackoverflow.com/ вопросы / 1733004 / python-next-function - person Helene; 14.05.2016
comment
Для всех, кто обеспокоен различиями в производительности между решениями os.walk и _2 _ + _ 3_: я только что протестировал каталог с 10 000 подкаталогов (с миллионами файлов в иерархии ниже), и различия в производительности незначительны. os.walk: 10 циклов, лучшее из 3: 44,6 мс на цикл и _5 _ + _ 6_: 10 циклов, лучшее из 3: 45,1 мс на цикл - person kevinmicke; 28.02.2017
comment
@kevinmicke попробуйте этот тест производительности на сетевом диске, я думаю, вы обнаружите, что производительность в этом случае довольно значительна. - person UKMonkey; 21.11.2017
comment
@UKMonkey Я уверен, что вы правы в том, что такой вариант использования может существенно отличаться. - person kevinmicke; 02.06.2018

Вы можете просто использовать glob.glob

from glob import glob
glob("/path/to/directory/*/")

Не забывайте конечный / после *.

person Udit Bansal    schedule 05.04.2016
comment
Отлично. Простой. Только он оставляет в конце / в именах - person juanmirocks; 21.03.2018
comment
Если вы не можете считать / разделителем папок, сделайте следующее: glob(os.path.join(path_to_directory, "*", "")) - person juanmirocks; 21.03.2018
comment
Это не работает для подкаталогов! Чтобы использовать glob, вот полный ответ: Используйте Glob () для рекурсивно находить файлы в Python? - person poppie; 12.10.2018
comment
чтобы сделать глоб рекурсивным, вы можете просто добавить следующий аргумент recursive=True - person JacoSolari; 12.11.2019

Намного лучше, чем указано выше, потому что вам не нужно несколько os.path.join (), и вы получите полный путь напрямую (если хотите), вы можете сделать это в Python 3.5 и выше. .

subfolders = [ f.path for f in os.scandir(folder) if f.is_dir() ]

Это даст полный путь к подкаталогу. Если вам нужно только имя подкаталога, используйте f.name вместо f.path

https://docs.python.org/3/library/os.html#os.scandir


Слегка ОТ: если вам нужно рекурсивно все подпапки и / или все файлы рекурсивно, взгляните на эту функцию, которая быстрее, чем os.walk & glob, и вернет список всех вложенных папок, а также всех файлов внутри этих (вложенных) вложенных папок: https://stackoverflow.com/a/59803793/2441026 < / а>

Если вы хотите рекурсивно только все подпапки:

def fast_scandir(dirname):
    subfolders= [f.path for f in os.scandir(dirname) if f.is_dir()]
    for dirname in list(subfolders):
        subfolders.extend(fast_scandir(dirname))
    return subfolders

Возвращает список всех вложенных папок с их полными путями. Это снова быстрее, чем os.walk, и намного быстрее, чем glob.


Анализ всех функций

tl; dr:
- Если вы хотите получить все подкаталоги немедленно для папки, используйте os.scandir.
- Если вы хотите получить все подкаталоги, даже < em> вложенные, используйте os.walk или - немного быстрее - указанную выше функцию fast_scandir.
- Никогда не используйте os.walk только для подкаталогов верхнего уровня, так как это может быть в сотни (!) раз медленнее, чем os.scandir.


Результаты:

os.scandir      took   1 ms. Found dirs: 439
os.walk         took 463 ms. Found dirs: 441 -> it found the nested one + base folder.
glob.glob       took  20 ms. Found dirs: 439
pathlib.iterdir took  18 ms. Found dirs: 439
os.listdir      took  18 ms. Found dirs: 439

Протестировано с W7x64, Python 3.8.1.

# -*- coding: utf-8 -*-
# Python 3


import time
import os
from glob import glob
from pathlib import Path


directory = r"<insert_folder>"
RUNS = 1


def run_os_walk():
    a = time.time_ns()
    for i in range(RUNS):
        fu = [x[0] for x in os.walk(directory)]
    print(f"os.walk\t\t\ttook {(time.time_ns() - a) / 1000 / 1000 / RUNS:.0f} ms. Found dirs: {len(fu)}")


def run_glob():
    a = time.time_ns()
    for i in range(RUNS):
        fu = glob(directory + "/*/")
    print(f"glob.glob\t\ttook {(time.time_ns() - a) / 1000 / 1000 / RUNS:.0f} ms. Found dirs: {len(fu)}")


def run_pathlib_iterdir():
    a = time.time_ns()
    for i in range(RUNS):
        dirname = Path(directory)
        fu = [f for f in dirname.iterdir() if f.is_dir()]
    print(f"pathlib.iterdir\ttook {(time.time_ns() - a) / 1000 / 1000 / RUNS:.0f} ms. Found dirs: {len(fu)}")


def run_os_listdir():
    a = time.time_ns()
    for i in range(RUNS):
        dirname = Path(directory)
        fu = [os.path.join(directory, o) for o in os.listdir(directory) if os.path.isdir(os.path.join(directory, o))]
    print(f"os.listdir\t\ttook {(time.time_ns() - a) / 1000 / 1000 / RUNS:.0f} ms. Found dirs: {len(fu)}")


def run_os_scandir():
    a = time.time_ns()
    for i in range(RUNS):
        fu = [f.path for f in os.scandir(directory) if f.is_dir()]
    print(f"os.scandir\t\ttook {(time.time_ns() - a) / 1000 / 1000 / RUNS:.0f} ms.\tFound dirs: {len(fu)}")


if __name__ == '__main__':
    run_os_scandir()
    run_os_walk()
    run_glob()
    run_pathlib_iterdir()
    run_os_listdir()
person user136036    schedule 31.10.2016
comment
было бы хорошо, если бы вы упомянули в начале своего вопроса, где вы заменяете различные функции, которые вы профилируете. Как бы то ни было, впечатляюще вы потратили на это время. Молодец. Я лично предпочитаю использовать одну библиотеку, поэтому мне понравился using pathlib` следующим образом `[f for f in p.iterdir () if f.is_dir ()]` ` - person Charlie Parker; 20.07.2020
comment
У меня есть 50 подкаталогов, каждый с тысячами подкаталогов. Я просто пробовал запустить fast_scandir, и это занимает больше часа. Это нормально? Могу ли я что-нибудь сделать, чтобы это ускорить? - person Vincent; 18.08.2020

Если вам нужно рекурсивное решение, которое найдет все подкаталоги в подкаталогах, используйте walk, как предлагалось ранее.

Если вам нужны только дочерние каталоги текущего каталога, объедините os.listdir с os.path.isdir

person Eli Bendersky    schedule 10.06.2009
comment
с pathlib проще: [f for f in p.iterdir() if f.is_dir()] - person Charlie Parker; 20.07.2020
comment
@CharlieParker: этот ответ появился на несколько лет раньше pathlib. - person Eli Bendersky; 20.07.2020

Python 3.4 представил модуль pathlib в стандартной библиотеке, которая обеспечивает объектно-ориентированную подход к обработке путей файловой системы:

from pathlib import Path

p = Path('./')

# All subdirectories in the current directory, not recursive.
[f for f in p.iterdir() if f.is_dir()]

Чтобы рекурсивно перечислить все подкаталоги, можно использовать подстановку пути с шаблоном ** .

# This will also include the current directory '.'
list(p.glob('**'))

Обратите внимание, что один * в качестве шаблона глобуса будет включать и файлы, и каталоги нерекурсивно. Чтобы получить только каталоги, можно добавить завершающий /, но это работает только при прямом использовании библиотеки glob, а не при использовании glob через pathlib:

import glob

# These three lines return both files and directories
list(p.glob('*'))
list(p.glob('*/'))
glob.glob('*')

# Whereas this returns only directories
glob.glob('*/')

Таким образом, Path('./').glob('**') соответствует тем же путям, что и glob.glob('**/', recursive=True).

Pathlib также доступен в Python 2.7 через модуль pathlib2 в PyPi.

person joelostblom    schedule 28.05.2017
comment
Чтобы перебрать список подкаталогов, вот хороший чистый синтаксис: for f in filter(Path.is_dir, p.iterdir()): - person Bryan Roach; 26.10.2019
comment
Вы уверены, что вам нужны две звезды для вашего решения с глобусом? gloab(*/) недостаточно? Тем не менее, потрясающий ответ, особенно для вашего чистого использования pathlib. Было бы неплохо прокомментировать, если он также допускает рекурсию, хотя из заголовка вопроса, который не нужен, и будущие читатели должны прочитать документы, на которые вы ссылаетесь. - person Charlie Parker; 20.07.2020
comment
Спасибо @CharlieParker! Я обновил свой ответ подробностями о рекурсии и использовании завершающей косой черты (в том числе отмечая, что конечные косые черты не нужны при использовании ** с глобусом pathlib. Что касается использования одной звездочки, это будет соответствовать файлам и каталогам нерекурсивно. - person joelostblom; 20.07.2020
comment
glob.glob('**/', recursive=True) не будет включать скрытые каталоги, но Path('./').glob('**') включает - person nos; 05.07.2021

Я предпочитаю использовать фильтр (https://docs.python.org/2/library/functions.html#filter), но это дело вкуса.

d='.'
filter(lambda x: os.path.isdir(os.path.join(d, x)), os.listdir(d))
person svelten    schedule 10.09.2015
comment
с pathlib проще: [f for f in p.iterdir() if f.is_dir()] - person Charlie Parker; 20.07.2020

Реализовано это с помощью python-os-walk. (http://www.pythonforbeginners.com/code-snippets-source-code/python-os-walk/).

import os

print("root prints out directories only from what you specified")
print("dirs prints out sub-directories from root")
print("files prints out all files from root and directories")
print("*" * 20)

for root, dirs, files in os.walk("/var/log"):
    print(root)
    print(dirs)
    print(files)
person Charith De Silva    schedule 26.09.2013
comment
с pathlib проще: [f for f in p.iterdir() if f.is_dir()] - person Charlie Parker; 20.07.2020

Выводить только каталоги

print("\nWe are listing out only the directories in current directory -")
directories_in_curdir = filter(os.path.isdir, os.listdir(os.curdir))
print(directories_in_curdir)

Выводить только файлы в текущем каталоге

files = filter(os.path.isfile, os.listdir(os.curdir))
print("\nThe following are the list of all files in the current directory -")
print(files)
person NutJobb    schedule 30.08.2016
comment
Не работал на Mac OS. Я думаю, что проблема в том, что os.listdir возвращает только имя каталога, а не полный путь, но os.path.isdir возвращает только True, если полный путь - это каталог. - person denson; 22.11.2016
comment
Это работает вне текущего каталога, если вы немного измените строку: subdirs = filter (os.path.isdir, [os.path.join (dir, x) for x in os.listdir (dir)]) - person RLC; 07.05.2019
comment
хорошая работа, избегая определения лямбда-функций и просто передавая функции напрямую. - person Charlie Parker; 20.07.2020

Вы можете получить список подкаталогов (и файлов) в Python 2.7, используя os.listdir (путь)

import os
os.listdir(path)  # list of subdirectories and files
person Oscar Martin    schedule 07.10.2014
comment
Сюда также входят файлы. - person Tarnay Kálmán; 15.10.2014
comment
Имя сбивает с толку, поскольку «dir» относится не к объектам, составляющим список, а к каталогу контейнера. Пожалуйста, проверьте свои однострочные ответы, для начинающих очень заманчиво их выбрать. - person Titou; 16.09.2016
comment
Остерегайтесь того, что os.listdir перечисляет содержимое каталога, включая файлы. - person guneysus; 26.10.2016

Поскольку я наткнулся на эту проблему, используя пути Python 3.4 и Windows UNC, вот вариант для этой среды:

from pathlib import WindowsPath

def SubDirPath (d):
    return [f for f in d.iterdir() if f.is_dir()]

subdirs = SubDirPath(WindowsPath(r'\\file01.acme.local\home$'))
print(subdirs)

Pathlib впервые появился в Python 3.4 и значительно упрощает работу с путями в разных операционных системах: https://docs.python.org/3.4/library/pathlib.html

person Marcus Schommler    schedule 10.11.2014

Хотя на этот вопрос давно дан ответ. Я хочу порекомендовать использовать модуль pathlib, поскольку это надежный способ работы в ОС Windows и Unix.

Итак, чтобы получить все пути в определенном каталоге, включая подкаталоги:

from pathlib import Path
paths = list(Path('myhomefolder', 'folder').glob('**/*.txt'))

# all sorts of operations
file = paths[0]
file.name
file.stem
file.parent
file.suffix

и т.п.

person Joost Döbken    schedule 07.07.2016

Спасибо за советы ребята. У меня возникла проблема с возвращением программных ссылок (бесконечная рекурсия) в виде каталогов. Софтлинки? Мы не хотим никаких вонючих софт-ссылок! Так...

Это отображало только каталоги, а не мягкие ссылки:

>>> import os
>>> inf = os.walk('.')
>>> [x[0] for x in inf]
['.', './iamadir']
person KurtB    schedule 10.05.2013
comment
Что [x[0] for x in inf] называется в Python, чтобы я мог его найти? - person shinzou; 23.12.2017
comment
@shinzou Это понимание списка. Супер полезно. Также поищите слова dict. - person KurtB; 23.02.2018

Скопируйте и вставьте в ipython:

import os
d='.'
folders = list(filter(lambda x: os.path.isdir(os.path.join(d, x)), os.listdir(d)))

Вывод из print(folders):

['folderA', 'folderB']
person Andrew Schreiber    schedule 11.10.2018
comment
Что такое X в этом случае? - person Abhishek Parikh; 28.10.2018
comment
@AbhishekParikh x - это элемент из списка, созданного os.listdir(d), потому что listdir вернет файлы и папки, которые он использует команду filter с os.path.isdir, чтобы отфильтровать любые файлы из списка. - person James Burke; 28.05.2019

Вот несколько простых функций, основанных на примере @Blair Conrad:

import os

def get_subdirs(dir):
    "Get a list of immediate subdirectories"
    return next(os.walk(dir))[1]

def get_subfiles(dir):
    "Get a list of immediate subfiles"
    return next(os.walk(dir))[2]
person Brian Burns    schedule 19.07.2017

Вот как я это делаю.

    import os
    for x in os.listdir(os.getcwd()):
        if os.path.isdir(x):
            print(x)
person Mujeeb Ishaque    schedule 09.10.2019
comment
Не работает. Я предполагаю, что в x вы должны указать полный путь для проверки с помощью isdir () - person niranjan patidar; 20.03.2020
comment
Вероятно, у вас проблемы с os.getcwd (); По сути, вы можете получить абсолютный путь и использовать его вместо этого. dir = os.path.dirname (os.path.abspath (файл)) - person Mujeeb Ishaque; 20.03.2020
comment
используя os, у меня работал pat.join (). Потому что это помогло получить полный путь к подкаталогу. - person niranjan patidar; 25.03.2020

Основываясь на решении Эли Бендерски, используйте следующий пример:

import os
test_directory = <your_directory>
for child in os.listdir(test_directory):
    test_path = os.path.join(test_directory, child)
    if os.path.isdir(test_path):
        print test_path
        # Do stuff to the directory "test_path"

где <your_directory> - это путь к каталогу, по которому вы хотите пройти.

person Blairg23    schedule 04.01.2016

С полным путем и учетом пути ., .., \\, ..\\..\\subfolder и т. Д .:

import os, pprint
pprint.pprint([os.path.join(os.path.abspath(path), x[0]) \
    for x in os.walk(os.path.abspath(path))])
person DevPlayer    schedule 06.10.2013

Кажется, этого ответа еще не существовало.

directories = [ x for x in os.listdir('.') if os.path.isdir(x) ]
person Andrew    schedule 23.02.2017
comment
Это всегда будет возвращать пустой список, если вы ищете что-либо, кроме текущего рабочего каталога, что технически и пытается сделать OP, но не очень многоразово. - person ochawkeye; 23.02.2017
comment
каталоги = [x для x в os.listdir (localDir), если os.path.isdir (localDir + x) - person Poonam; 15.02.2018

Недавно у меня был аналогичный вопрос, и я обнаружил, что лучший ответ для python 3.6 (как добавлено пользователем havlock) - использовать os.scandir. Поскольку кажется, что с его помощью нет решения, я добавлю свое. Во-первых, нерекурсивное решение, в котором перечислены только подкаталоги непосредственно в корневом каталоге.

def get_dirlist(rootdir):

    dirlist = []

    with os.scandir(rootdir) as rit:
        for entry in rit:
            if not entry.name.startswith('.') and entry.is_dir():
                dirlist.append(entry.path)

    dirlist.sort() # Optional, in case you want sorted directory names
    return dirlist

Рекурсивная версия будет выглядеть так:

def get_dirlist(rootdir):

    dirlist = []

    with os.scandir(rootdir) as rit:
        for entry in rit:
            if not entry.name.startswith('.') and entry.is_dir():
                dirlist.append(entry.path)
                dirlist += get_dirlist(entry.path)

    dirlist.sort() # Optional, in case you want sorted directory names
    return dirlist

имейте в виду, что entry.path имеет абсолютный путь к подкаталогу. Если вам нужно только имя папки, вы можете использовать вместо него entry.name. См. os.DirEntry. для получения дополнительных сведений об объекте entry.

person Alberto A    schedule 16.02.2018
comment
Собственно, как это написано, на 3.5 работать не будет, только 3.6. Для использования на 3.5 вам необходимо удалить диспетчер контекста - см. stackoverflow.com/questions/41401417/ - person havlock; 01.04.2018
comment
Это правильно. Могу поклясться, что где-то читал, что диспетчер контекста был реализован в версии 3.5, но, похоже, я ошибаюсь. - person Alberto A; 02.04.2018

Самый простой способ:

from pathlib import Path
from glob import glob

current_dir = Path.cwd()
all_sub_dir_paths = glob(str(current_dir) + '/*/') # returns list of sub directory paths

all_sub_dir_names = [Path(sub_dir).name for sub_dir in all_sub_dir_paths] 
person Amir Afianian    schedule 27.09.2020

используйте функцию фильтра os.path.isdir поверх os.listdir() примерно так filter(os.path.isdir,[os.path.join(os.path.abspath('PATH'),p) for p in os.listdir('PATH/')])

person oneLeggedChicken    schedule 08.02.2016

Это перечислит все подкаталоги прямо вниз по дереву файлов.

import pathlib


def list_dir(dir):
    path = pathlib.Path(dir)
    dir = []
    try:
        for item in path.iterdir():
            if item.is_dir():
                dir.append(item)
                dir = dir + list_dir(item)
        return dir
    except FileNotFoundError:
        print('Invalid directory')

pathlib является новым в версии 3.4

person Yossarian42    schedule 06.05.2019

Функция для возврата списка всех подкаталогов в пределах заданного пути к файлу. Будет искать во всем дереве файлов.

import os

def get_sub_directory_paths(start_directory, sub_directories):
    """
    This method iterates through all subdirectory paths of a given 
    directory to collect all directory paths.

    :param start_directory: The starting directory path.
    :param sub_directories: A List that all subdirectory paths will be 
        stored to.
    :return: A List of all sub-directory paths.
    """

    for item in os.listdir(start_directory):
        full_path = os.path.join(start_directory, item)

        if os.path.isdir(full_path):
            sub_directories.append(full_path)

            # Recursive call to search through all subdirectories.
            get_sub_directory_paths(full_path, sub_directories)

return sub_directories
person Matthew Ashley    schedule 16.08.2019

мы можем получить список всех папок с помощью os.walk ()

import os

path = os.getcwd()

pathObject = os.walk(path)

этот pathObject является объектом, и мы можем получить массив,

arr = [x for x in pathObject]

arr is of type [('current directory', [array of folder in current directory], [files in current directory]),('subdirectory', [array of folder in subdirectory], [files in subdirectory]) ....]

Мы можем получить список всех подкаталогов, перебирая arr и печатая средний массив

for i in arr:
   for j in i[1]:
      print(j)

Это напечатает весь подкаталог.

Чтобы получить все файлы:

for i in arr:
   for j in i[2]:
      print(i[0] + "/" + j)
person Shivam Kesarwani    schedule 07.01.2020

Присоединившись к нескольким решениям отсюда, я в итоге использовал следующее:

import os
import glob

def list_dirs(path):
    return [os.path.basename(x) for x in filter(
        os.path.isdir, glob.glob(os.path.join(path, '*')))]
person SadSeven    schedule 04.03.2020

Этот ниже класс сможет получить список файлов, папок и всех подпапок внутри данного каталога.

import os
import json

class GetDirectoryList():
    def __init__(self, path):
        self.main_path = path
        self.absolute_path = []
        self.relative_path = []


    def get_files_and_folders(self, resp, path):
        all = os.listdir(path)
        resp["files"] = []
        for file_folder in all:
            if file_folder != "." and file_folder != "..":
                if os.path.isdir(path + "/" + file_folder):
                    resp[file_folder] = {}
                    self.get_files_and_folders(resp=resp[file_folder], path= path + "/" + file_folder)
                else:
                    resp["files"].append(file_folder)
                    self.absolute_path.append(path.replace(self.main_path + "/", "") + "/" + file_folder)
                    self.relative_path.append(path + "/" + file_folder)
        return resp, self.relative_path, self.absolute_path

    @property
    def get_all_files_folder(self):
        self.resp = {self.main_path: {}}
        all = self.get_files_and_folders(self.resp[self.main_path], self.main_path)
        return all

if __name__ == '__main__':
    mylib = GetDirectoryList(path="sample_folder")
    file_list = mylib.get_all_files_folder
    print (json.dumps(file_list))

В то время как примерный каталог выглядит как

sample_folder/
    lib_a/
        lib_c/
            lib_e/
                __init__.py
                a.txt
            __init__.py
            b.txt
            c.txt
        lib_d/
            __init__.py
        __init__.py
        d.txt
    lib_b/
        __init__.py
        e.txt
    __init__.py

Результат получен

[
  {
    "files": [
      "__init__.py"
    ],
    "lib_b": {
      "files": [
        "__init__.py",
        "e.txt"
      ]
    },
    "lib_a": {
      "files": [
        "__init__.py",
        "d.txt"
      ],
      "lib_c": {
        "files": [
          "__init__.py",
          "c.txt",
          "b.txt"
        ],
        "lib_e": {
          "files": [
            "__init__.py",
            "a.txt"
          ]
        }
      },
      "lib_d": {
        "files": [
          "__init__.py"
        ]
      }
    }
  },
  [
    "sample_folder/lib_b/__init__.py",
    "sample_folder/lib_b/e.txt",
    "sample_folder/__init__.py",
    "sample_folder/lib_a/lib_c/lib_e/__init__.py",
    "sample_folder/lib_a/lib_c/lib_e/a.txt",
    "sample_folder/lib_a/lib_c/__init__.py",
    "sample_folder/lib_a/lib_c/c.txt",
    "sample_folder/lib_a/lib_c/b.txt",
    "sample_folder/lib_a/lib_d/__init__.py",
    "sample_folder/lib_a/__init__.py",
    "sample_folder/lib_a/d.txt"
  ],
  [
    "lib_b/__init__.py",
    "lib_b/e.txt",
    "sample_folder/__init__.py",
    "lib_a/lib_c/lib_e/__init__.py",
    "lib_a/lib_c/lib_e/a.txt",
    "lib_a/lib_c/__init__.py",
    "lib_a/lib_c/c.txt",
    "lib_a/lib_c/b.txt",
    "lib_a/lib_d/__init__.py",
    "lib_a/__init__.py",
    "lib_a/d.txt"
  ]
]
person Saurabh Pandey    schedule 04.02.2021

Эта функция с заданным родителем directory рекурсивно перебирает все свои directories и prints все filenames, которые она находит внутри. Слишком полезно.

import os

def printDirectoryFiles(directory):
   for filename in os.listdir(directory):  
        full_path=os.path.join(directory, filename)
        if not os.path.isdir(full_path): 
            print( full_path + "\n")


def checkFolders(directory):

    dir_list = next(os.walk(directory))[1]

    #print(dir_list)

    for dir in dir_list:           
        print(dir)
        checkFolders(directory +"/"+ dir) 

    printDirectoryFiles(directory)       

main_dir="C:/Users/S0082448/Desktop/carpeta1"

checkFolders(main_dir)


input("Press enter to exit ;")

person dbz    schedule 03.06.2019

Есть много хороших ответов, но если вы пришли сюда в поисках простого способа получить список всех файлов или папок сразу. Вы можете воспользоваться преимуществами операционной системы, предлагаемой find в Linux и Mac, которая намного быстрее, чем os.walk.

import os
all_files_list = os.popen("find path/to/my_base_folder -type f").read().splitlines()
all_sub_directories_list = os.popen("find path/to/my_base_folder -type d").read().splitlines()

OR

import os

def get_files(path):
    all_files_list = os.popen(f"find {path} -type f").read().splitlines()
    return all_files_list

def get_sub_folders(path):
    all_sub_directories_list = os.popen(f"find {path} -type d").read().splitlines()
    return all_sub_directories_list
person Pardhu    schedule 03.09.2020

Это должно сработать, поскольку оно также создает дерево каталогов;

import os
import pathlib

def tree(directory):
    print(f'+ {directory}')
    print("There are " + str(len(os.listdir(os.getcwd()))) + \
    " folders in this directory;")
    for path in sorted(directory.glob('*')):
        depth = len(path.relative_to(directory).parts)
        spacer = '    ' * depth
        print(f'{spacer}+ {path.name}')

В нем должны быть перечислены все каталоги в папке, использующей библиотеку pathlib. path.relative_to(directory).parts получает элементы относительно текущего рабочего каталога.

person MLDev    schedule 11.11.2020

person    schedule
comment
обратите внимание, что в этом подходе вам нужно позаботиться о проблемах с abspath, если они не выполняются на '.' - person daspostloch; 30.05.2011
comment
Просто предупреждаем, если вы не используете cwd ('.'), Это не сработает, если вы не выполните os.path.join на o, чтобы получить полный путь, иначе isdir(0) всегда будет возвращать false - person James McMahon; 23.08.2012
comment
Похоже, что сообщение было обновлено с исправлениями для двух упомянутых выше проблем. - person cgmb; 12.11.2015
comment
Чтобы не вызывать os.path.join дважды, вы можете сначала присоединиться, а затем отфильтровать список, используя os.path.isdir: filter(os.path.isdir, [os.path.join(d, o) for o in os.listdir(d)]) - person quant_dev; 14.06.2019
comment
Использование pathlib с [f for f in data_path.iterdir() if f.is_dir()] или glob намного проще и легче для чтения: glob.glob("/path/to/directory/*/"). - person Charlie Parker; 20.07.2020