我试图使用Directory.GetFiles()方法检索多种类型的文件列表,如mp3的和jpg的。以下两种方法我都试过了,但都没有成功:
Directory.GetFiles("C:\\path", "*.mp3|*.jpg", SearchOption.AllDirectories);
Directory.GetFiles("C:\\path", "*.mp3;*.jpg", SearchOption.AllDirectories);
有没有办法一次就能搞定?
我试图使用Directory.GetFiles()方法检索多种类型的文件列表,如mp3的和jpg的。以下两种方法我都试过了,但都没有成功:
Directory.GetFiles("C:\\path", "*.mp3|*.jpg", SearchOption.AllDirectories);
Directory.GetFiles("C:\\path", "*.mp3;*.jpg", SearchOption.AllDirectories);
有没有办法一次就能搞定?
当前回答
for
var exts = new[] { "mp3", "jpg" };
你可以:
public IEnumerable<string> FilterFiles(string path, params string[] exts) {
return
Directory
.EnumerateFiles(path, "*.*")
.Where(file => exts.Any(x => file.EndsWith(x, StringComparison.OrdinalIgnoreCase)));
}
不要忘记新的。net 4目录。EnumerateFiles用于性能提升(目录和文件的区别是什么?EnumerateFiles vs Directory.GetFiles?) “IgnoreCase”应该比“ToLower”(。EndsWith("aspx", stringcompare . ordinalignorecase)而不是。tolower ().EndsWith("aspx"))
但EnumerateFiles的真正好处体现在你拆分过滤器并合并结果时:
public IEnumerable<string> FilterFiles(string path, params string[] exts) {
return
exts.Select(x => "*." + x) // turn into globs
.SelectMany(x =>
Directory.EnumerateFiles(path, x)
);
}
如果你不需要将它们转换为glob(即exts = new[] {"*.mp3", "*.jpg"}),它会变得更快一些。
基于以下LinqPad测试的性能评估(注意:Perf只是重复委托10000次) https://gist.github.com/zaus/7454021
(从'duplicate'重新发布和扩展,因为这个问题特别要求没有LINQ:多个文件扩展searchPattern for System.IO.Directory.GetFiles)
其他回答
如果你使用VB。NET(或将依赖导入到你的c#项目中),实际上存在一个方便的方法,允许过滤多个扩展:
Microsoft.VisualBasic.FileIO.FileSystem.GetFiles("C:\\path", Microsoft.VisualBasic.FileIO.SearchOption.SearchAllSubDirectories, new string[] {"*.mp3", "*.jpg"});
在VB。NET可以通过My-namespace访问:
My.Computer.FileSystem.GetFiles("C:\path", FileIO.SearchOption.SearchAllSubDirectories, {"*.mp3", "*.jpg"})
不幸的是,这些方便的方法不支持像Directory.EnumerateFiles()那样的惰性求值变体。
是什么
string[] filesPNG = Directory.GetFiles(path, "*.png");
string[] filesJPG = Directory.GetFiles(path, "*.jpg");
string[] filesJPEG = Directory.GetFiles(path, "*.jpeg");
int totalArraySizeAll = filesPNG.Length + filesJPG.Length + filesJPEG.Length;
List<string> filesAll = new List<string>(totalArraySizeAll);
filesAll.AddRange(filesPNG);
filesAll.AddRange(filesJPG);
filesAll.AddRange(filesJPEG);
没有。试试下面的方法:
List<string> _searchPatternList = new List<string>();
...
List<string> fileList = new List<string>();
foreach ( string ext in _searchPatternList )
{
foreach ( string subFile in Directory.GetFiles( folderName, ext )
{
fileList.Add( subFile );
}
}
// Sort alpabetically
fileList.Sort();
// Add files to the file browser control
foreach ( string fileName in fileList )
{
...;
}
摘自:http://blogs.msdn.com/markda/archive/2006/04/20/580075.aspx
如果你有一个很大的扩展列表要检查,你可以使用下面的。我不想创建很多OR语句,所以我修改了lette写的东西。
string supportedExtensions = "*.jpg,*.gif,*.png,*.bmp,*.jpe,*.jpeg,*.wmf,*.emf,*.xbm,*.ico,*.eps,*.tif,*.tiff,*.g01,*.g02,*.g03,*.g04,*.g05,*.g06,*.g07,*.g08";
foreach (string imageFile in Directory.GetFiles(_tempDirectory, "*.*", SearchOption.AllDirectories).Where(s => supportedExtensions.Contains(Path.GetExtension(s).ToLower())))
{
//do work here
}
另一种使用Linq的方式,但是不需要返回所有内容并在内存中过滤。
var files = Directory.GetFiles("C:\\path", "*.mp3", SearchOption.AllDirectories).Union(Directory.GetFiles("C:\\path", "*.jpg", SearchOption.AllDirectories));
它实际上是对GetFiles()的2次调用,但我认为这与问题的精神是一致的,并以一个可枚举的形式返回它们。