这两种异步方法的区别是什么?

本文关键字:是什么 区别 两种 异步方法 | 更新日期: 2023-09-27 18:06:47

这两种异步方法有什么区别?如果没有,这两种方法在什么情况下会不同?

谢谢。

public async Task<int> MyMethod1Async()
{
    return 1;
}
public async Task<int> MyMethod2Async()
{
    return await new Task<int>(() => 1);
}

这两种异步方法的区别是什么?

看一下这两种方法:

public async Task<int> MyMethod1Async()
{
    return 1;
}

这将同步运行,因为其中没有"await"操作符-它只是返回1,所以它与您刚刚执行的操作没有什么不同:

public int MyMethod1()
{
    return 1;
}

下面的方法可能更好地说明了async的不同"类型"之间的区别:

    public async Task<string> MyMethod1Async()
    {
        using (HttpClient client = new HttpClient())
        {
            client.BaseAddress = new Uri("SomeBaseAddress");
            // This will return control to the method's caller until this gets a result from the server
            HttpResponseMessage message = await client.GetAsync("SomeURI");
            // The same as above - returns control to the method's caller until this is done
            string content = await message.Content.ReadAsStringAsync();
            return content;
        }
    }
像这样的代码不一定会产生额外的线程(除非微软碰巧实现了那些特定的库调用)。不管怎样,await/async 需要创建额外的线程;它可以在同一线程上异步运行 我对这一事实的标准说明如下:假设你去一家有10个人的餐馆。当服务员经过时,他问的第一个人还没有准备好;然而,另外9个人是。因此,服务员向其他9个人要了他们的菜,然后回到原来的那个人身边,希望他能在那之前准备好点餐。(他们绝对不会再找一个服务员来等原来的服务员来点餐,而且这样做可能也不会节省多少时间)。这就是async/await在很多情况下的工作方式(例外的是一些Task Parallel库调用,比如Thread.Run(…),实际上在其他线程上执行的——在我们的例子中,引入了第二个服务员——所以请确保您检查了文档,以确定哪个是哪个)。

你列出的下一项不会工作,因为你只是创建了任务,你实际上没有对它做任何事情:

public async Task<int> MyMethod2Async()
{
    return await new Task<int>(() => 1);
}

我假设您实际上打算做以下事情:

public async Task<int> MyMethod2Async()
{
    return await Task.Run<int>(() => 1);
}

这将在线程池中运行lambda表达式,将控制权返回给MyMethod2Async的调用者,直到lambda表达式有结果,然后一旦有结果就返回lambda表达式的值。

总而言之,区别在于你是在同一个线程上异步运行(相当于你桌子前的第一个人告诉服务员在其他人点完餐后再回来),还是在一个单独的线程上运行任务。

冒着过度简化的风险,cpu密集型任务通常应该在后台线程中异步运行。然而,io绑定的任务(或者其他等待外部系统某种结果的情况)通常可以在同一个线程上异步运行;与在同一线程上异步执行相比,将其放在后台线程上并不一定会有很大的性能改进。

第一个方法返回一个Result1的已经完成的任务。

第二个方法返回一个永远不会完成的Task<int>