测量异步代码片段的执行时间

时间:2017-02-17 17:26:32

标签: c# asynchronous async-await

我在测量异步代码片段的执行时间方面遇到问题,所以我创建了一个控制台应用程序,以便于测试。我试图查看下载200MB文件所需的时间是否与程序的输出相对应。但是,在代码片段的第一个命令以输出“22 ms”结束后,应用程序立即停止执行。任何想法为什么会发生这种情况?

在我的真实应用程序中,GUI本身就是多线程的,测量的时间也是不切实际的。我尝试将“Task.Delay”调用插入到代码段中,它似乎对测量值没有影响。

为了简洁起见,我缩短了真实应用程序的代码。任何想法为什么这不起作用?关于如何衡量异步代码片段执行时间的其他想法?

class Program
{
    static void Main(string[] args)
    {
        MainAsync().GetAwaiter().GetResult();
    }

    private static async Task MainAsync()
    {
        var httpClient = new HttpClient();

        await MeasureExecutionTimeAsync(
            async () => {
                // download a 200MB file
                var response = await httpClient.GetAsync("http://web4host.net/200MB.zip");

                // this never gets executed
                var array = await response.Content.ReadAsByteArrayAsync();
                File.WriteAllBytes("C:/mytmp/bytefile.xxx", array);
            }
        );
    }

    private static async Task MeasureExecutionTimeAsync(Action measuredAction)
    {
        var stopwatch = new Stopwatch();
        stopwatch.Start();

        await Task.Run(measuredAction);

        stopwatch.Stop();

        Console.WriteLine(stopwatch.ElapsedMilliseconds + " ms");
    }
}

1 个答案:

答案 0 :(得分:1)

问题似乎与行

有关
await Task.Run(measuredAction);

试试这个

private static async Task MainAsync()
    {
        var httpClient = new HttpClient();

        Func<Task> action = async () =>
        {
            var response = await httpClient.GetAsync("http://web4host.net/200MB.zip").ConfigureAwait(false);

            // this never gets executed
            var array = await response.Content.ReadAsByteArrayAsync();
            File.WriteAllBytes("C:/mytmp/bytefile.xxx", array);
            return;
        };

        await MeasureExecutionTimeAsync(action);
    }

    private static async Task MeasureExecutionTimeAsync(Func<Task> measuredAction)
    {
        var stopwatch = new Stopwatch();
        stopwatch.Start();

        await measuredAction.Invoke();

        stopwatch.Stop();

        Console.WriteLine(stopwatch.ElapsedMilliseconds + " ms");
    }