为什么.net中没有异步文件删除?

时间:2012-05-15 18:02:26

标签: .net file-io asynchronous

你有读写的异步版本(开始/结束函数),但没有删除(我可以告诉)。这有什么理由吗?是不是有很多理由像读/写一样异步删除?

使用线程来模拟异步行为与异步函数不同。差别很大,确定你得到了感知的并行处理,但它并没有真正阻止阻塞,其他线程仍然被阻止等待文件i / o完成。真正的异步函数(开始/结束函数)在系统级运行,它们排队文件i / o,让应用程序继续运行,并让应用程序知道何时可以继续执行文件i / o(允许你在等待文件i / o可用时执行其他操作。

6 个答案:

答案 0 :(得分:26)

这会很有用。如果在断开连接的网络共享上删除,则DeleteFile最多可能需要30秒。

原因可能是没有本机函数来异步删除文件。托管API通常是非托管API的包装器。

答案 1 :(得分:15)

这个怎么样:

public static class FileExtensions {
   public static Task DeleteAsync(this FileInfo fi) {
      return Task.Factory.StartNew(() => fi.Delete() );
   }
}

然后你可以这样做:

FileInfo fi = new FileInfo(fileName);
await fi.DeleteAsync(); // C# 5
fi.DeleteAsync().Wait(); // C# 4

答案 2 :(得分:5)

如果没有其他文件打开,打开FileStream FileOptions.DeleteOnClose将导致Windows在关闭流时删除该文件。如果您已经打开FileStream进行异步读/写操作,这可能对您有所帮助,但如果您需要等待删除完成它对您没有帮助(尽管根据@JoelFan等待{{ 1}}完成并不保证文件实际上已被删除了。)

有趣的是,在对网络共享进行测试时,似乎打开流并且不执行任何操作比File.Delete明显更快(~40%):

File.Delete

答案 3 :(得分:2)

File类不公开异步文件删除方法;但是,通过使用FileStream类,仍然可以通过利用提供的13个构造函数重载中的特定一个来执行异步文件删除。下面的代码应该加载一个文件,将其设置为零字节,然后删除它;所有异步。

using (new FileStream(Path, FileMode.Truncate, FileAccess.ReadWrite, FileShare.Delete, 1, FileOptions.DeleteOnClose | FileOptions.Asynchronous)) ;

我没有对它进行过多次测试,因此您可能需要稍微修改一下使用情况。此外,由于它不返回任何Task的派生,因此使用Task.Run方法运行它可能是有效的。基本上,它执行文件删除,这在I / O级别上实际上是异步的,因此在这种情况下将其卸载到线程池上应该没问题。

答案 4 :(得分:0)

我可能错了,但是如果有人试图在跨线程操作中访问同一个文件,则需要阻止文件进行访问,直到删除操作完成。

答案 5 :(得分:-2)

也许是因为你可以自己轻松地做到这一点?

var t = Task.Factory.StartNew(() => File.Delete("file.txt"));
// ...
t.Wait();