readdir()
La fonction PHP readdir() lit une entrée à la fois dans un répertoire ouvert avec opendir(). Découvrez sa syntaxe et ses patterns d'utilisation.
La fonction PHP readdir() lit une entrée à la fois dans un répertoire que vous avez déjà ouvert avec opendir(). Chaque appel renvoie le nom du fichier ou sous-répertoire suivant et fait avancer un pointeur interne, ce qui permet de parcourir tous les éléments d'un dossier en bouclant. Cette page explique la syntaxe, la valeur de retour, le pattern de boucle qui évite un bogue courant, et la façon dont readdir() se compare aux alternatives de plus haut niveau.
Syntaxe
readdir(resource $dir_handle = null): string|false$dir_handle— un descripteur de répertoire renvoyé paropendir(). Si vous l'omettez, PHP utilise le dernier descripteur ouvert paropendir().- Valeur de retour — le nom de fichier de l'entrée suivante sous forme de string, ou
falselorsqu'il n'y a plus d'entrées. Les entrées incluent les noms spéciaux.(répertoire courant) et..(répertoire parent), et elles sont renvoyées dans l'ordre où le système de fichiers les stocke, sans tri.
Lecture d'un répertoire
Pour utiliser readdir(), ouvrez d'abord un descripteur de répertoire avec opendir(), bouclez avec readdir() jusqu'à ce qu'il retourne false, puis libérez le descripteur avec closedir() :
<?php
$dir = __DIR__; // the directory this script lives in
if ($handle = opendir($dir)) {
while (false !== ($entry = readdir($handle))) {
if ($entry !== "." && $entry !== "..") {
echo "$entry\n";
}
}
closedir($handle);
}Ce code ouvre le répertoire, parcourt son contenu et affiche chaque nom à l'exception de . et ... L'appel à closedir() libère le descripteur une fois terminé.
Pourquoi false !== et non une simple vérification de véracité
La comparaison stricte false !== ($entry = readdir($handle)) est essentielle, pas stylistique. Un répertoire peut légitimement contenir une entrée nommée "0", et une vérification de chaîne vide se comporterait aussi mal. PHP traite la string "0" comme fausse, donc écrire while ($entry = readdir($handle)) stopperait la boucle prématurément dès qu'elle atteindrait un tel fichier. Comparer strictement contre false fait que la boucle se termine seulement quand readdir() n'a vraiment plus d'entrées.
Filtrage des entrées par extension
readdir() renvoie des noms bruts, donc tout filtrage vous incombe. Combinez-le avec pathinfo() pour ne conserver que les types de fichiers qui vous intéressent — ici, des images :
<?php
$dir = __DIR__;
$allowed = ['jpg', 'jpeg', 'png', 'gif'];
if ($handle = opendir($dir)) {
while (false !== ($entry = readdir($handle))) {
$extension = strtolower(pathinfo($entry, PATHINFO_EXTENSION));
if ($entry !== "." && $entry !== ".." && in_array($extension, $allowed, true)) {
echo "$entry\n";
}
}
closedir($handle);
}pathinfo($entry, PATHINFO_EXTENSION) extrait l'extension de chaque nom, et in_array(..., true) (mode strict) la vérifie par rapport à la liste d'autorisation afin de n'afficher que les fichiers correspondants.
Relecture du même répertoire
Puisque chaque appel à readdir() fait avancer le pointeur interne, une seconde boucle sur le même descripteur ne renvoie rien — le pointeur est déjà à la fin. Utilisez rewinddir() pour le réinitialiser à la première entrée sans rouvrir le répertoire :
<?php
$handle = opendir(__DIR__);
while (false !== ($entry = readdir($handle))) { /* first pass */ }
rewinddir($handle); // back to the start
while (false !== ($entry = readdir($handle))) {
// second pass sees every entry again
}
closedir($handle);readdir() vs scandir() vs glob()
readdir() est le bloc de construction de bas niveau. Dans la plupart du code moderne, on préfère une alternative à appel unique :
scandir()renvoie toutes les entrées sous forme de tableau trié en un seul appel — sans la gestion deopendir/closedir.glob()correspond à un pattern de style shell (par exemple*.png) et renvoie des chemins complets, ce qui rend le filtrage par extension très simple.
Utilisez readdir() quand vous souhaitez traiter les entrées une par une sans charger toute la liste en mémoire (utile pour les très grands répertoires), ou quand vous avez besoin d'un contrôle précis sur l'itération.
Pièges courants
- Toujours ignorer
.et..—readdir()les inclut, et oublier de les filtrer est le bogue le plus fréquent, surtout dans les parcours récursifs de répertoires. opendir()peut échouer. Si le chemin n'existe pas ou n'est pas lisible, il retournefalseet émet un avertissement, c'est pourquoi les exemples protègent la boucle avecif ($handle = opendir($dir)).- Fermez vos descripteurs. Appelez
closedir()(ou laissez le script se terminer) pour libérer la ressource. - L'ordre n'est pas garanti. Si vous avez besoin d'une sortie triée, utilisez
scandir()ou triez vous-même les noms.