You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

为何Windows上C#异步IO同步执行?与.NET文档不符原因探究

.NET异步文件IO在Windows下的并行执行异常问题

根据.NET文档说明,异步IO命令可用于并行执行文件操作,但实际测试发现Windows平台下存在不符合预期的行为:

测试代码

public static async Task SimpleParallelWriteByteAsync()
{
    var rootFilePath = "C:/temp/asynctest2";
    var fileSize = 1024 * 1024 * 100;

    if (Directory.Exists(rootFilePath))
        Directory.Delete(rootFilePath, true);
    Directory.CreateDirectory(rootFilePath);
                
    var buffer = new byte[fileSize];
    new Random().NextBytes(buffer);

    IList<Task> writeTaskList = new List<Task>();

    Stopwatch sw = Stopwatch.StartNew(); 
    for (int index = 0; index <= 10; index += 1)
    {
        string fileName = $"file-{index:00}.txt";
        string filePath = Path.Combine(rootFilePath, fileName);
        writeTaskList.Add(File.WriteAllBytesAsync(filePath, buffer));
    }
    var timespanLoop = sw.Elapsed;
    await Task.WhenAll(writeTaskList);
    var timespanAfterWhenall = sw.Elapsed;

    Console.WriteLine($"loop {timespanLoop} after when all {timespanAfterWhenall}");
}

Windows平台测试结果

运行后输出:

loop 00:00:05.6234609 after when all 00:00:05.6254815

两个时间值差异极小,说明循环过程中异步写入实际是串行执行的。这一现象在本地SSD、网络驱动器,以及net472、net6.0、net8.0环境中均可复现。

修改代码后的结果

将添加任务的代码改为:

writeTaskList.Add(Task.Run(() => File.WriteAllBytesAsync(filePath, buffer)));

执行后得到预期的并行输出:

loop 00:00:00.0089046 after when all 00:00:01.2339927

Linux平台测试结果

在Linux上,原异步代码可正常并行执行,输出示例:

00:00:00.0082008 after when all 00:00:03.0910144

疑问

  • 是什么机制控制了Windows平台下的这一行为?
  • 为何.NET文档的描述与实际行为存在差异?
    按照异步IO的设计原理,异步文件操作无需占用线程,只需向操作系统发送异步写入请求,待操作完成后由操作系统通知.NET即可。

内容的提问来源于stack exchange,提问作者Nick

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.29 14:00:20