83 votes

Comment filtrer le Répertoire.EnumerateFiles avec de multiples critères?

J'ai le code suivant:

List<string> result = new List<string>();

foreach (string file in Directory.EnumerateFiles(path,"*.*",  
      SearchOption.AllDirectories)
      .Where(s => s.EndsWith(".mp3") || s.EndsWith(".wma")))
       {
          result.Add(file);                 
       }

Il fonctionne très bien et fait ce dont j'ai besoin. Sauf pour une petite chose. Je voudrais trouver une meilleure façon de filtrer sur plusieurs extensions. Je voudrais utiliser un tableau de chaînes avec des filtres comme ceci:

string[] extensions = { "*.mp3", "*.wma", "*.mp4", "*.wav" };

Quel est le moyen le plus efficace pour ce faire à l'aide de NET Framework 4.0/LINQ? Toutes les suggestions?

J'apprécierais toute aide étant un programmeur occasionnel :-)

88voto

Mikael Svenson Points 18243

J'ai créé certaines méthodes d'aide à résoudre ce dont j'ai blogué plus tôt cette année.

Une version prend une expression régulière pattern \.mp3|\.mp4, et de l'autre une liste de chaînes et s'exécute en parallèle.

public static class MyDirectory
{   // Regex version
   public static IEnumerable<string> GetFiles(string path, 
                       string searchPatternExpression = "",
                       SearchOption searchOption = SearchOption.TopDirectoryOnly)
   {
      Regex reSearchPattern = new Regex(searchPatternExpression);
      return Directory.EnumerateFiles(path, "*", searchOption)
                      .Where(file =>
                               reSearchPattern.IsMatch(Path.GetExtension(file)));
   }

   // Takes same patterns, and executes in parallel
   public static IEnumerable<string> GetFiles(string path, 
                       string[] searchPatterns, 
                       SearchOption searchOption = SearchOption.TopDirectoryOnly)
   {
      return searchPatterns.AsParallel()
             .SelectMany(searchPattern => 
                    Directory.EnumerateFiles(path, searchPattern, searchOption));
   }
}

30voto

Henk Holterman Points 153608

Dépouillé de LINQ contexte, cela revient à ho comment savoir si un fichier correspond à une liste d'extensions. System.IO.Path.GetExtension() est un meilleur choix ici qu' String.EndsWith(). Les multiples || peut être remplacé par .Contains() ou .IndexOf() selon les collections.

var extensions = new HashSet<string>(StringComparer.OrdinalIgnoreCase)  
   {  ".mp3", ".wma", ".mp4", ".wav" };

...  s => extensions.Contains(Path.GetExtension(s))

18voto

Islam Yahiatene Points 632
string path = "C:\\";
var result = new List<string>();
string[] extensions = { ".mp3", ".wma", ".mp4", ".wav" };

foreach (string file in Directory.EnumerateFiles(path, "*.*", SearchOption.AllDirectories)
    .Where(s => extensions.Any(ext => ext == Path.GetExtension(s))))
{
    result.Add(file);
    Console.WriteLine(file);
}

2voto

kmcbrearty Points 21

Je sais que c'est un vieux post, mais je suis venu avec une solution de gens à utiliser.

private IEnumerable<FileInfo> FindFiles()
{
    DirectoryInfo sourceDirectory = new DirectoryInfo(@"C:\temp\mydirectory");
    string foldersFilter = "*bin*,*obj*";
    string fileTypesFilter = "*.mp3,*.wma,*.mp4,*.wav";

    // filter by folder name and extension
    IEnumerable<DirectoryInfo> directories = foldersFilter.Split(',').SelectMany(pattern => sourceDirectory.EnumerateDirectories(pattern, SearchOption.AllDirectories));
    List<FileInfo> files = new List<FileInfo>();
    files.AddRange(directories.SelectMany(dir => fileTypesFilter.Split(',').SelectMany(pattern => dir.EnumerateFiles(pattern, SearchOption.AllDirectories))));

    // Pick up root files
    files.AddRange(fileTypesFilter.Split(',').SelectMany(pattern => sourceDirectory.EnumerateFiles(fileTypesFilter, SearchOption.TopDirectoryOnly)));

    // filter just by extension
    IEnumerable<FileInfo> files2 = fileTypesFilter.Split(',').SelectMany(pattern => sourceDirectory.EnumerateFiles(pattern, SearchOption.AllDirectories));
}

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X