8
votes

Obtenir des fichiers récursives: sautez les fichiers / répertoires qui ne peuvent pas être lus?

Je veux obtenir tous les fichiers d'un répertoire dans un tableau (y compris les fichiers des sous-dossiers) xxx

Le problème avec ceci est: si une exception est levée la commande complète des arrêts de commande . Y a-t-il un meilleur moyen de le faire de manière à ce que si un dossier ne peut pas être accédé, cela ne saura que le sauter?


3 commentaires

Juger par le @ "c: \" , je pense qu'il demande si l'appel de la méthode peut terminer son travail et obtenir tous les répertoires où l'accès est accordé.


Le getfiles montre un exemple de recouvrement manuellement et il ne serait pas difficile d'ajouter une exception de la manipulation de l'exception. Je suis supposer le problème de ne pas être capable de lire Sous-Annuaire des sous-répertoires ; et qu'un annuaire.getfiles (.., Sans_recursive_search) fonctionnera comme tout-ou-rien pour le répertoire spécifique comme prévu.


(Bien que cet exemple soit simpliste: le résultat n'est que des effets secondaires et des "mauvaises choses" se produiront s'il existe des jonctions ou des liens de répertoire récursifs.)


4 Réponses :


6
votes

Vous devrez probablement faire un peu plus de dactylographie, puis écrivez un walker de répertoire comme celui-ci:

    public static string[] FindAllFiles(string rootDir) {
        var pathsToSearch = new Queue<string>();
        var foundFiles = new List<string>();

        pathsToSearch.Enqueue(rootDir);

        while (pathsToSearch.Count > 0) {
            var dir = pathsToSearch.Dequeue();

            try {
                var files = Directory.GetFiles(dir);
                foreach (var file in Directory.GetFiles(dir)) {
                    foundFiles.Add(file);
                }

                foreach (var subDir in Directory.GetDirectories(dir)) {
                    pathsToSearch.Enqueue(subDir);
                }

            } catch (Exception /* TODO: catch correct exception */) {
                // Swallow.  Gulp!
            }
        }

        return foundFiles.ToArray();
    }


4 commentaires

Choses de NOTE: 1) Ceci est une implémentation BFS, pas un DFS. 2) Cela ne traitera pas de structures récursives (point de jonction ou liens durs / mous dans NTFS) 3) toarray semble idiot.


@pst accepte les points 2 et 3 ( toarray était de produire la même chaîne [] comme dans la question et n'est pas du tout nécessaire), mais le point 1 fait-il beaucoup Différence si tous les sous-répertoires accessibles doivent être traversés?


@ikh je ne dis pas que c'est mauvais du tout, c'est-à-dire que c'est :) C'est la différence entre traverser par ordre de: c: \ a \ c: \ b \ c: \ a \ aa \ (largeur d'abord) et c: \ a \ c: \ a \ aa \ c: \ b \ (Profond-premier) - Certains peuvent s'attendre à ce que l'autre comportement (DFS) ainsi C'est quelque chose à garder à l'esprit.


Cela a fonctionné parfaitement! Ceci est beaucoup plus lent que la version intégrée - mais bien sûr, ils ne traitent pas les fichiers non-atteints.



-1
votes

Essayez ceci:

DirectoryInfo directory = new DirectoryInfo(@"c:\");
        DirectoryInfo[] folders = directory.GetDirectories("*", SearchOption.AllDirectories);

        List<string> files = new List<string>();
        foreach (DirectoryInfo info in folders)
        {
            foreach (FileInfo file in info.GetFiles())
            {
                files.Add(file.Name);
            }
        }


1 commentaires

Que se passe-t-il s'il y a un dossier c: \ nopermissionstoread ?



-1
votes

ou essayez celui-ci: xxx

ou noms de fichier sans extension: xxx


1 commentaires

Comment cela va-t-il gérer / agir dans des cas où le répertoire ne peut pas être lu?



0
votes

Directory.getfiles ne peut pas ignorer les liens de symbole de répertoire qui causent souvent des boucles, puis des exceptions.

SO basé sur la réponse de @ iks et Vérifiez si un fichier est réel ou un lien symbolique , voici une version qui transmet le résultat sur le répertoire Go similaire.Enumènes : xxx


1 commentaires

Un point de reparse n'est pas nécessairement un lien symbolique! Cela obtiendra "de faux positifs". Reconnaître les véritables liens symboliques que vous devez utiliser des API natives. Une mise en œuvre de travail complète peut être trouvée ici: CodeProject.com / Articles / 15633 / ...