Configuration SearchPattern in EnumerateFiles
Asked Answered
N

5

7

I have a directory with 2 files:

  • file1.xls
  • file2.xlsx

If I do:

directoryInfo.EnumerateFiles("*.xls", SearchOption.TopDirectoryOnly)

It is returning both files, and I only want the first (file1.xls). How can I do this?

Thank you!

Nuri answered 30/5, 2012 at 7:56 Comment(0)
M
9

It looks like under the hood, the DirectoryInfo class uses the Win32 call FindFirstFile.

This only allows the wildcards:

* to match any character

? to match 0 or more characters - see comments.

Therefore you will have to filter the results yourself, perhaps using the following:

directoryInfo.EnumerateFiles("*.xls", SearchOption.TopDirectoryOnly)
             .Where(fi => fi.Extension == ".xls");
Mackie answered 30/5, 2012 at 8:31 Comment(1)
Thank you. Your answer its very completedNuri
G
3

This is actually an expected behaviour. It's odd, but it is documented.

On MSDN we can read a remark:

When using the asterisk wildcard character in a searchPattern, such as "*.txt", the matching behavior when the extension is exactly three characters long is different than when the extension is more or less than three characters long. A searchPattern with a file extension of exactly three characters returns files having an extension of three or more characters, where the first three characters match the file extension specified in the searchPattern. A searchPattern with a file extension of one, two, or more than three characters returns only files having extensions of exactly that length that match the file extension specified in the searchPattern. When using the question mark wildcard character, this method returns only files that match the specified file extension. For example, given two files, "file1.txt" and "file1.txtother", in a directory, a search pattern of "file?.txt" returns just the first file, while a search pattern of "file*.txt" returns both files.

Grendel answered 17/1, 2014 at 15:27 Comment(0)
A
1

Something like this:

directoryInfo.EnumerateFiles(".xls",SearchOption.TopDirectoryOnly)
    .Where( f => Path.GetExtension( f ) == ".xls" );
Alathia answered 30/5, 2012 at 8:23 Comment(4)
This doesn't compile, even if you include the searchPattern variable in the EnumerateFiles call. The enumerable is of type FileInfo (see my answer).Mackie
Yes, but this example has served me as the basis. Finally I do ExtensionsToSearch.SelectMany(pattern => directoryInfo.EnumerateFiles("*." + pattern, SearchOption.TopDirectoryOnly).Where(fileInfo => Path.GetExtension(fileInfo.FullName) == "." + pattern ))Nuri
@gt, Thanks I typed it from memory. I was thinking the class Directory as the basis not DirectoryInfo as was the question, for which I think it may have compiled.Alathia
@Nuri "Yes, but this example has served me as the basis." - it does the world no good to promote code that does not compile as gt saidCrenelate
T
0

you can use IEnumerable.First(), IEnumerable.FirstOrDefault() extention methods, or if pattern is important correct your enumeration search pattern.

Transpontine answered 30/5, 2012 at 8:13 Comment(1)
First or FirstOrDefault is not valid for me, because if in the directory have file1.xls, file2.xlsx and file3.xls I need file1.xls and file3.xls Your other option. How could I correct my enumeration search pattern?Nuri
A
0

This works using the .Except() and should be faster:

   var dir = new DirectoryInfo(myFolderPath);
   ICollection<FileInfo> files = dir.EnumerateFiles("*.xls").Except(dir.EnumerateFiles("*.xls?")).ToList();

You can use Union(s) to add more extensions. This is cleaner (I believe it's faster, though hadn't tested) overall. IMO

Apocryphal answered 15/3, 2018 at 2:2 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.