Gibt es eine Möglichkeit, eine Liste aller Unterverzeichnisse im aktuellen Verzeichnis in Python zurückzugeben?
Ich weiß, dass Sie dies mit Dateien tun können, aber ich muss stattdessen die Liste der Verzeichnisse abrufen.
Gibt es eine Möglichkeit, eine Liste aller Unterverzeichnisse im aktuellen Verzeichnis in Python zurückzugeben?
Ich weiß, dass Sie dies mit Dateien tun können, aber ich muss stattdessen die Liste der Verzeichnisse abrufen.
Antworten:
Meinen Sie unmittelbare Unterverzeichnisse oder jedes Verzeichnis direkt im Baum?
In beiden Fällen können Sie Folgendes os.walk
tun:
os.walk(directory)
gibt für jedes Unterverzeichnis ein Tupel aus. Dieser erste Eintrag im 3-Tupel ist also ein Verzeichnisname
[x[0] for x in os.walk(directory)]
sollte Ihnen alle Unterverzeichnisse rekursiv geben.
Beachten Sie, dass der zweite Eintrag im Tupel die Liste der untergeordneten Verzeichnisse des Eintrags an der ersten Position ist. Sie können ihn also stattdessen verwenden, aber es ist unwahrscheinlich, dass Sie viel sparen.
Sie können es jedoch nur verwenden, um Ihnen die unmittelbaren untergeordneten Verzeichnisse zu geben:
next(os.walk('.'))[1]
Oder sehen Sie sich die anderen bereits veröffentlichten Lösungen an, die os.listdir
und verwenden os.path.isdir
, einschließlich der unter " So erhalten Sie alle unmittelbaren Unterverzeichnisse in Python ".
os.walk('.').next()[1]
oder os.walk('.').__next__()[1]
direkt. Verwenden Sie stattdessen die integrierte Funktion next()
, die sowohl in Python 2 (siehe Dokument) als auch in Python 3 (siehe Dokument) verfügbar ist . Zum Beispiel : next(os.walk('.'))[1]
.
os.walk('.').next()[1]
direkt zu verwenden ?
iteraror.__next__()
es sich um eine interne Methode handelt und die iterator.next()
Verwendung next()
gemäß PEP-3114 auf die integrierte Methode umgestellt werden sollte . Siehe PEP-3114, das 2007 genehmigt wurde.
os.walk
und os.listdir
+ os.path.isdir
Lösungen machen: Ich habe gerade in einem Verzeichnis mit 10.000 Unterverzeichnissen (mit Millionen von Dateien in der folgenden Hierarchie) getestet, und die Leistungsunterschiede sind vernachlässigbar. os.walk
: "10 Schleifen, am besten 3: 44,6 ms pro Schleife" und os.listdir
+ os.path.isdir
: "10 Schleifen, am besten 3: 45,1 ms pro Schleife"
import os
d = '.'
[os.path.join(d, o) for o in os.listdir(d)
if os.path.isdir(os.path.join(d,o))]
os.path.join
On ausführen o
, um den vollständigen Pfad zu erhalten. Andernfalls isdir(0)
wird immer false zurückgegeben
os.path.join
zweimal os.path.isdir
filter(os.path.isdir, [os.path.join(d, o) for o in os.listdir(d)])
Sie könnten einfach verwenden glob.glob
from glob import glob
glob("/path/to/directory/*/")
Vergessen Sie nicht das Nachlaufen /
nach dem *
.
/
/
, der glob(os.path.join(path_to_directory, "*", ""))
recursive=True
Viel schöner als die oben genannten, da Sie nicht mehrere os.path.join () benötigen und den vollständigen Pfad direkt erhalten (wenn Sie dies wünschen), können Sie dies in Python 3.5 und höher tun .
subfolders = [ f.path for f in os.scandir(folder) if f.is_dir() ]
Dadurch wird der vollständige Pfad zum Unterverzeichnis angegeben. Wenn Sie nur den Namen des Unterverzeichnisses möchten, verwenden Sie f.name
stattdessenf.path
https://docs.python.org/3/library/os.html#os.scandir
Etwas OT: Wenn Sie alle Unterordner rekursiv und / oder alle Dateien rekursiv benötigen , sehen Sie sich diese Funktion an, die schneller als os.walk
& ist glob
und eine Liste aller Unterordner sowie aller Dateien in diesen (Unter-) Unterordnern zurückgibt: https://stackoverflow.com/a/59803793/2441026
Falls Sie nur alle Unterordner rekursiv möchten :
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
Gibt eine Liste aller Unterordner mit ihren vollständigen Pfaden zurück. Dies ist wieder schneller als os.walk
und viel schneller als glob
.
Eine Analyse aller Funktionen
tl; dr:
- Wenn Sie alle unmittelbaren Unterverzeichnisse für einen Ordner abrufen möchten, verwenden Sie os.scandir
.
- Wenn Sie alle Unterverzeichnisse abrufen möchten , auch verschachtelte , verwenden Sie os.walk
die fast_scandir
obige Funktion oder - etwas schneller - .
- Niemals os.walk
nur für Unterverzeichnisse der obersten Ebene verwenden, da dies hunderte (!) Mal langsamer sein kann als os.scandir
.
os.walk
wird der Basisordner sein. Sie erhalten also nicht nur Unterverzeichnisse. Sie können es verwenden fu.pop(0)
, um es zu entfernen.Ergebnisse :
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
Getestet mit 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()
Wenn Sie eine rekursive Lösung benötigen, die alle Unterverzeichnisse in den Unterverzeichnissen findet, verwenden Sie walk wie zuvor vorgeschlagen.
Wenn Sie nur die untergeordneten Verzeichnisse des aktuellen Verzeichnisses benötigen, kombinieren Sie os.listdir
mitos.path.isdir
Ich bevorzuge die Verwendung von Filtern ( https://docs.python.org/2/library/functions.html#filter ), aber dies ist nur eine Frage des Geschmacks.
d='.'
filter(lambda x: os.path.isdir(os.path.join(d, x)), os.listdir(d))
Implementiert dies mit 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)
Sie können die Liste der Unterverzeichnisse (und Dateien) in Python 2.7 mit os.listdir (Pfad) abrufen.
import os
os.listdir(path) # list of subdirectories and files
os.listdir
Inhalt des Verzeichnisses einschließlich der Dateien aufgelistet ist.
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)
Python 3.4 führte das pathlib
Modul in die Standardbibliothek ein, die einen objektorientierten Ansatz für die Verarbeitung von Dateisystempfaden bietet:
from pathlib import Path
p = Path('./')
# List comprehension
[f for f in p.iterdir() if f.is_dir()]
# The trailing slash to glob indicated directories
# This will also include the current directory '.'
list(p.glob('**/'))
Pathlib ist auch in Python 2.7 über das pathlib2-Modul auf PyPi verfügbar.
for f in filter(Path.is_dir, p.iterdir()):
Da ich bei der Verwendung von Python 3.4- und Windows UNC-Pfaden auf dieses Problem gestoßen bin, gibt es hier eine Variante für diese Umgebung:
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 ist neu in Python 3.4 und erleichtert die Arbeit mit Pfaden unter verschiedenen Betriebssystemen erheblich: https://docs.python.org/3.4/library/pathlib.html
Obwohl diese Frage schon vor langer Zeit beantwortet wurde. Ich möchte empfehlen, die zu verwendenpathlib
Modul zu verwenden, da dies eine robuste Methode ist, um unter Windows und Unix zu arbeiten.
So rufen Sie alle Pfade in einem bestimmten Verzeichnis ab, einschließlich der Unterverzeichnisse:
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
usw.
Danke für die Tipps, Leute. Ich bin auf ein Problem gestoßen, bei dem Softlinks (unendliche Rekursion) als Verzeichnisse zurückgegeben wurden. Softlinks? Wir wollen keine stinkenden Softlinks! Damit...
Dadurch wurden nur die Verzeichnisse und keine Softlinks gerendert:
>>> import os
>>> inf = os.walk('.')
>>> [x[0] for x in inf]
['.', './iamadir']
[x[0] for x in inf]
heißt Python, damit ich es nachschlagen kann?
Kopieren Einfügen freundlich in ipython
:
import os
d='.'
folders = list(filter(lambda x: os.path.isdir(os.path.join(d, x)), os.listdir(d)))
Ausgabe von print(folders)
:
['folderA', 'folderB']
x
ist das Element aus der Liste, das von erstellt wurde, os.listdir(d)
weil listdir
Dateien und Ordner zurückgegeben werden, mit denen er den filter
Befehl verwendet os.path.isdir
, um alle Dateien aus der Liste herauszufiltern.
So mache ich es.
import os
for x in os.listdir(os.getcwd()):
if os.path.isdir(x):
print(x)
Hier sind einige einfache Funktionen, die auf dem Beispiel von @Blair Conrad basieren:
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]
Verwenden Sie das folgende Beispiel, um auf der Lösung von Eli Bendersky aufzubauen:
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"
Wo <your_directory>
ist der Pfad zu dem Verzeichnis, das Sie durchlaufen möchten?
Diese Antwort schien noch nicht zu existieren.
directories = [ x for x in os.listdir('.') if os.path.isdir(x) ]
Ich hatte kürzlich eine ähnliche Frage und fand heraus, dass die beste Antwort für Python 3.6 (wie Benutzer Havlock hinzugefügt hat) die Verwendung ist os.scandir
. Da es anscheinend keine Lösung gibt, werde ich meine eigene hinzufügen. Erstens eine nicht rekursive Lösung, die nur die Unterverzeichnisse direkt unter dem Stammverzeichnis auflistet.
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
Die rekursive Version würde folgendermaßen aussehen:
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
Denken Sie daran, dass dies entry.path
den absoluten Pfad zum Unterverzeichnis darstellt. Falls Sie nur den Ordnernamen benötigen, können Sie entry.name
stattdessen verwenden. Weitere Informationen zum Objekt finden Sie unter os.DirEntryentry
.
Verwenden Sie eine Filterfunktion os.path.isdir
für so os.listdir()
etwasfilter(os.path.isdir,[os.path.join(os.path.abspath('PATH'),p) for p in os.listdir('PATH/')])
Dadurch werden alle Unterverzeichnisse direkt im Dateibaum aufgelistet.
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
ist neu in Version 3.4
Funktion zum Zurückgeben einer Liste aller Unterverzeichnisse innerhalb eines bestimmten Dateipfads. Durchsucht den gesamten Dateibaum.
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
Mit os.walk () können wir eine Liste aller Ordner abrufen.
import os
path = os.getcwd()
pathObject = os.walk(path)
Dieses pathObject ist ein Objekt und wir können ein Array von erhalten
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]) ....]
Wir können eine Liste aller Unterverzeichnisse erhalten, indem wir das arr durchlaufen und das mittlere Array drucken
for i in arr:
for j in i[1]:
print(j)
Dadurch wird das gesamte Unterverzeichnis gedruckt.
So erhalten Sie alle Dateien:
for i in arr:
for j in i[2]:
print(i[0] + "/" + j)
Diese Funktion mit einem bestimmten übergeordneten directory
Element durchläuft alle directories
rekursiven Funktionen und prints
alle filenames
darin enthaltenen Elemente. Zu nützlich.
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 ;")