HOWTO · Python
Ouvrir tous les fichiers d'un répertoire en Python
Lire les fichiers d'un répertoire avec os.listdir(), sélectionner les correspondances avec glob.glob(), parcourir les entrées avec os.scandir() ou inclure les répertoires imbriqués avec os.walk().
Sur cette page
Pour lire les fichiers texte d’un répertoire, utilisez os.listdir() pour un répertoire unique, glob.glob() pour sélectionner des noms selon un motif, os.scandir() pour inspecter les entrées, ou os.walk() pour inclure les répertoires imbriqués. Construisez les chemins avec les noms renvoyés et utilisez open() dans une instruction with. Ces exemples lisent du texte ; les fichiers binaires nécessitent le mode binaire tel que "rb" ou un analyseur spécifique au format.
Ouvrir des fichiers dans un répertoire avec os.walk()
Utilisez os.walk() lorsque les fichiers peuvent se trouver dans le répertoire de départ ou dans n’importe quel répertoire en dessous. À chaque itération, elle produit trois valeurs : le chemin du répertoire actuel (root), les noms de ses répertoires enfants (dirnames) et les noms des fichiers directement dans ce répertoire (filenames). Joignez root et chaque nom de fichier pour obtenir un chemin ; joindre uniquement le répertoire de départ et le nom de fichier manquerait les fichiers dans les répertoires imbriqués.
Cet exemple crée une petite arborescence de répertoires afin de pouvoir s’exécuter tel quel. Le tri des noms de répertoires et de fichiers rend l’ordre de traitement prévisible pour ce montage ; l’ordre de parcours des répertoires n’est sinon pas garanti.
Exécutez cet exemple :
import os
import tempfile
with tempfile.TemporaryDirectory() as directory:
nested = os.path.join(directory, "notes")
os.mkdir(nested)
for folder, name, contents in [
(directory, "summary.txt", "Ready"),
(nested, "details.txt", "More notes"),
]:
with open(os.path.join(folder, name), "w", encoding="utf-8") as file:
file.write(contents)
for root, dirnames, filenames in os.walk(directory):
dirnames.sort()
for filename in sorted(filenames):
path = os.path.join(root, filename)
with open(path, encoding="utf-8") as file:
print(f"{filename}: {file.read()}")
os.walk() peut parcourir de haut en bas ou de bas en haut. La valeur par défaut est de haut en bas, ce qui convient lorsque les fichiers sont traités au fur et à mesure de leur découverte. L’exemple utilise explicitement UTF-8 ; choisissez un encodage qui correspond à vos fichiers texte. Si les fichiers utilisent des encodages différents, traitez ces fichiers selon le format plutôt que de supposer qu’un seul encodage fonctionne pour tous. Pour les répertoires que votre processus ne peut pas lire, gérez les erreurs du système de fichiers qui en résultent selon les besoins de votre application.
Ouvrir des fichiers dans un répertoire avec os.listdir()
os.listdir() renvoie les noms des entrées directement à l’intérieur d’un répertoire. Elle ne descend pas dans les répertoires enfants, et son résultat peut inclure à la fois des fichiers et des répertoires. Joignez chaque nom au chemin du répertoire et vérifiez os.path.isfile() avant de l’ouvrir, comme indiqué ci-dessous.
import os
import tempfile
with tempfile.TemporaryDirectory() as directory:
with open(os.path.join(directory, "one.txt"), "w", encoding="utf-8") as file:
file.write("First file")
os.mkdir(os.path.join(directory, "archive"))
for name in sorted(os.listdir(directory)):
path = os.path.join(directory, name)
if os.path.isfile(path):
with open(path, encoding="utf-8") as file:
print(f"{name}: {file.read()}")
Cette approche est utile lorsque vous voulez chaque fichier ordinaire d’un répertoire et n’avez pas besoin de recherche par motif. La vérification os.path.isfile() suit les liens symboliques vers les fichiers ; si votre application doit distinguer les liens ou appliquer une politique différente, utilisez les vérifications de chemin ou d’entrée de répertoire appropriées. Conservez le bloc with autour de chaque fichier afin que Python le ferme après la lecture, y compris si le traitement ultérieur quitte ce bloc plus tôt.
Ouvrir les fichiers correspondants avec glob.glob()
glob.glob() sélectionne des chemins à l’aide d’un motif de nom de fichier. Un motif tel que *.txt correspond aux fichiers texte directement dans le répertoire nommé ; il ne recherche pas par lui-même dans les répertoires enfants. Les chemins renvoyés peuvent être passés directement à open(). Utilisez os.walk() lorsque la tâche consiste à visiter un arbre entier, ou construisez délibérément un motif récursif si c’est ce qu’il vous faut.
import glob
import os
import tempfile
with tempfile.TemporaryDirectory() as directory:
for name, contents in [("readme.txt", "Instructions"), ("data.csv", "id")]:
with open(os.path.join(directory, name), "w", encoding="utf-8") as file:
file.write(contents)
pattern = os.path.join(directory, "*.txt")
for path in sorted(glob.glob(pattern)):
with open(path, encoding="utf-8") as file:
print(f"{os.path.basename(path)}: {file.read()}")
Modifiez le composant final du motif pour sélectionner un autre ensemble de noms de fichiers, tel que report-*.csv. Le tri des correspondances est utile lorsque le travail ultérieur dépend d’un ordre stable. Un motif peut également correspondre à des noms de répertoires, donc filtrez les chemins correspondants avec os.path.isfile() si le motif n’est pas limité aux fichiers.
Ouvrir des fichiers dans un répertoire avec os.scandir()
os.scandir() produit des objets d’entrée de répertoire qui exposent le nom et le chemin de chaque entrée et fournissent des méthodes telles que is_file(). Elle est utile lorsque la boucle doit vérifier une entrée avant de l’ouvrir ou inspecter les informations de l’entrée. L’itérateur est un gestionnaire de contexte, utilisez donc with pour le fermer lorsque l’itération se termine. Cet exemple vérifie les entrées et lit les fichiers ordinaires ; il ne descend pas dans les répertoires enfants.
import os
import tempfile
with tempfile.TemporaryDirectory() as directory:
with open(os.path.join(directory, "notes.txt"), "w", encoding="utf-8") as file:
file.write("Scanned text")
os.mkdir(os.path.join(directory, "archive"))
with os.scandir(directory) as entries:
for entry in sorted(entries, key=lambda item: item.name):
if entry.is_file():
with open(entry.path, encoding="utf-8") as file:
print(f"{entry.name}: {file.read()}")
entry.name est le nom au sein du répertoire analysé, tandis que entry.path est le chemin à utiliser lors de l’ouverture de cette entrée. Comme os.listdir(), un seul appel à os.scandir() ne couvre qu’un seul répertoire. Si les entrées peuvent changer entre la vérification et l’ouverture, l’état du système de fichiers peut changer pendant cet intervalle, donc le code qui gère des répertoires non fiables ou modifiés simultanément devrait également tenir compte des erreurs au moment de l’ouverture.
Choisir la bonne méthode pour votre répertoire
Choisissez os.listdir() pour un passage simple et non récursif sur un répertoire. Choisissez glob.glob() lorsqu’un motif de nom de fichier doit décider quels chemins traiter. Choisissez os.walk() lorsque les fichiers dans les répertoires imbriqués font partie de la tâche. Choisissez os.scandir() lorsque chaque entrée nécessite une vérification de fichier ou d’autres informations sur l’entrée avant d’agir.
Les quatre méthodes énumèrent le contenu des répertoires, mais l’ordre d’énumération n’est pas garanti ; triez les noms ou les chemins lorsque la répétabilité du traitement compte. Les exemples utilisent des objets fichier gérés par contexte et le mode texte UTF-8. Adaptez l’encodage aux fichiers source, et utilisez le mode binaire ou un analyseur lorsque les fichiers ne sont pas du texte brut. Les permissions d’accès, les fichiers qui disparaissent pendant le traitement et les différences d’encodage propres à l’application peuvent nécessiter un traitement supplémentaire dans le code de production.