Po pierwsze, wybacz mój biedny angielski; o) Miałem problem, który zabrał mnie na tę stronę: wyliczyć pliki katalogu i jego podkatalogów bez blokowania na wyjątku UnauthorizedAccessException i, podobnie jak nowa metoda .Net 4 DirectoryInfo .Zanumeruj ..., uzyskaj pierwszy wynik przed zakończeniem całego zapytania.
Z pomocą różnych przykładów znalezionych tu i tam w internecie, w końcu napisać tę metodę:
public static IEnumerable<FileInfo> EnumerateFiles_Recursive(this DirectoryInfo directory, string searchPattern, SearchOption searchOption, Func<DirectoryInfo, Exception, bool> handleExceptionAccess)
{
Queue<DirectoryInfo> subDirectories = new Queue<DirectoryInfo>();
IEnumerable<FileSystemInfo> entries = null;
// Try to get an enumerator on fileSystemInfos of directory
try
{
entries = directory.EnumerateFileSystemInfos(searchPattern, SearchOption.TopDirectoryOnly);
}
catch (Exception e)
{
// If there's a callback delegate and this delegate return true, we don't throw the exception
if (handleExceptionAccess == null || !handleExceptionAccess(directory, e))
throw;
// If the exception wasn't throw, we make entries reference an empty collection
entries = EmptyFileSystemInfos;
}
// Yield return file entries of the directory and enqueue the subdirectories
foreach (FileSystemInfo entrie in entries)
{
if (entrie is FileInfo)
yield return (FileInfo)entrie;
else if (entrie is DirectoryInfo)
subDirectories.Enqueue((DirectoryInfo)entrie);
}
// If recursive search, we make recursive call on the method to yield return entries of the subdirectories.
if (searchOption == SearchOption.AllDirectories)
{
DirectoryInfo subDir = null;
while (subDirectories.Count > 0)
{
subDir = subDirectories.Dequeue();
foreach (FileInfo file in subDir.EnumerateFiles_Recursive(searchPattern, searchOption, handleExceptionAccess))
{
yield return file;
}
}
}
else
subDirectories.Clear();
}
używać kolejki i metody rekurencyjnej zachować tradycyjny porządek (zawartość katalogu, a następnie zawartość pierwszego podkatalogu i jego własnych podkatalogów, a następnie zawartość drugiego ...). Parametr "handleExceptionAccess" jest po prostu wywołaniem funkcji, gdy zostanie zgłoszony wyjątek z katalogiem; funkcja musi zwracać wartość true, aby wskazać, że wyjątek musi zostać zignorowany.
Z tego Methode, można napisać:
DirectoryInfo dir = new DirectoryInfo("c:\\temp");
long size = dir.EnumerateFiles_Recursive("*", SearchOption.AllDirectories, (d, ex) => true).Sum(f => f.Length);
I tu jesteśmy: wszystkie wyjątek, gdy próbuje wyliczyć katalog będzie ignorować!
Nadzieja ta pomoc
Lionel
PS: z jakiegoś powodu nie mogę wyjaśnić, moja metoda jest bardziej szybkie niż jeden Framework 4 ...
PPS: można dostać mój testowe rozwiązania ze źródłem dla tych metod: tutaj TestDirEnumerate. Piszę EnumerateFiles_Recursive, EnumerateFiles_NonRecursive (użyj kolejki, aby uniknąć rekursji) i EnumerateFiles_NonRecursive_TraditionalOrder (użyj stosu kolejki, aby uniknąć rekursji i zachować tradycyjną kolejność). Trzymaj te 3 metody bez zainteresowania, piszę je tylko dla sprawdzenia najlepszego. Myślę, że zatrzymam tylko ostatnią. Napisałem również odpowiednik dla EnumerateFileSystemInfos i EnumerateDirectories.
Dzięki za to :) – ThePower