Strange thing about .NET 4.0 filesystem enumeration functionality
I just read a page of "Whats new .NET Framework 4.0". I have trouble understanding the last paragraph:
To remove open handles on enumerated directories or files
Create a custom method (or function in Visual Basic) to contain your enumeration code.
Apply the MethodImplAttribute attribute with the NoInlining option to the new method. For example:
[MethodImplAttribute(MethodImplOptions.NoInlining)]
Private void Enumerate()
Include the following method calls, to run after your enumeration code:
* The GC.Collect() method (no parameters). * The GC.WaitForPendingFinalizers() method.
Why the attribute NoInlining? What harm would inlining do here?
Why call the garbage collector manually, why not making the enumerator implement IDisposable in the first place? I suspect they use FindFirstFile()/FindNextFile() API calls for开发者_Python百科 the imlementation, so FindClose() has to be called in any case if the enumeration is done.
EDIT:
Does anybody have an idea why the NoInlining attribute is suggested in the article?
Pretty bizarre. The iterator correctly implements IDisposable, it calls FindClose(). The AllDirectories options could be a source of trouble since FindFileFirst/Next only allows iterating a single directory. But I'm seeing the iterator doing the right thing, it only keeps a single handle open while iterating the directory structure.
The MSDN article specifically mentions "if there is an open handle that remains on one of the enumerated directories or files". FindFileFirst/Next won't leave a handle open. But sloppy user code that reads files while enumerating does. "a delete operation on a file or directory" is relevant too, I think the behavior changed in Vista. A DeleteFile() can succeed but the file won't actually disappear until all handles on the file are closed.
We need somebody to volunteer and not implement this code on XP. I reckon we'll find someone soon :)
精彩评论