简体   繁体   English

C# 多个异步任务以及当它们相互使用完成时在哪里正确等待它们?

[英]C# multiple async tasks and where to properly await them when they use each other to complete?

I have two methods that are similar, however, after theorizing about this, I'm pretty sure they are different in execution.我有两种相似的方法,但是,在对此进行理论分析之后,我很确定它们在执行上是不同的。

MethodOne:方法一:

        var renderDocumentDirective = await 
        RenderDocumentBuilder.Instance.GetRenderDocumentDirectiveAsync(previousPage, session);

        return await ResponseClient.Instance.BuildAlexaResponse(new Response()
        {
            shouldEndSession = null,
            directives = new List<IDirective>()
            {
                renderDocumentDirective
            }

        }, session.alexaSessionDisplayType);

MethodTwo方法二

            var renderDocumentDirective = RenderDocumentBuilder.Instance.GetRenderDocumentDirectiveAsync(previousPage, session);
            return await ResponseClient.Instance.BuildAlexaResponse(new Response()
            {
                shouldEndSession = null,
                directives = new List<IDirective>()
                {
                    await renderDocumentDirective
                }

            }, session.alexaSessionDisplayType);

The first method uses the await operator on the async task, RenderDocumentBuilder , prior to its uses inside the ResponseClient , which is also an async task.第一种方法在异步任务RenderDocumentBuilder上使用 await 运算符,然后在ResponseClient ,这也是一个异步任务。

However the second method, sets up the Task RenderDocumentBuilder , but doesn't call the awaited method until it is inside the ResponseClient , which, at this point in execution, is waiting to return data.然而,第二种方法设置了 Task RenderDocumentBuilder ,但直到它位于ResponseClient内部时才调用等待的方法,此时它正在等待返回数据。

Both ways of executing this method work, but I am unclear if it is proper to:执行此方法的两种方式都有效,但我不清楚它是否适合:

  • await a task outside the ResponseClient?等待 ResponseClient 之外的任务? (method 1) (方法一)

  • Or, is it proper to create the renderDocumentDirective Task outside the ResponseClient and await it inside the method?或者,在 ResponseClient 外部创建 renderDocumentDirective 任​​务并在方法内部等待它是否合适? (method 2) (方法二)

I think you misinterpret the flow of data.我认为您误解了数据流。

Here are your two methods written a bit more verbose这是你写得更冗长的两种方法

Method 1方法一

var renderTask = RenderDocumentBuilder.Instance.GetRenderDocumentDirectiveAsync(previousPage, session);

var renderDocumentDirective = await renderTask;

var alexaResponse = new Response();

alexaResponse.shouldEndSession = null,
alexaResponse.directives = new List<IDirective>();
alexaResponse.directives.Add(renderDocumentDirective);

var buildTask = ResponseClient.Instance.BuildAlexaResponse(alexaResponse, session.alexaSessionDisplayType);

return await buildTask;

Method 2方法二

var renderTask = RenderDocumentBuilder.Instance.GetRenderDocumentDirectiveAsync(previousPage, session);

var alexaResponse = new Response()
alexaResponse.shouldEndSession = null,
alexaResponse.directives = new List<IDirective>();
alexaResponse.directives.Add(await renderTask);

var buildTask = ResponseClient.Instance.BuildAlexaResponse(alexaResponse, session.alexaSessionDisplayType);

return await buildTask;

So you see that the only real difference is that methode 2 creates the Response object, sets shouldEndSession and creates the List object before or it awaits the renderTask .所以你看到唯一真正的区别是方法 2 创建Response对象,设置shouldEndSession并在之前创建List对象,或者它等待renderTask

Method 2 might be beneficial, but this depends on how GetRenderDocumentDirectiveAsync is implemented (ie truely async).方法 2 可能是有益的,但这取决于GetRenderDocumentDirectiveAsync的实现方式(即真正的异步)。 But even if it is, it is highly unlikly that method 2 brings any performance gains as there is not much difference between both methods.但即使是这样,方法 2 也不太可能带来任何性能提升,因为这两种方法之间没有太大区别。

That said, I would go with method 1, because it looks more like sync code and in most cases you want to await a Task as soon you have it available, because await/async is mainly about freeing threads to do other stuff and not about parallalism.也就是说,我会使用方法 1,因为它看起来更像是同步代码,并且在大多数情况下,您希望在任务可用时尽快等待它,因为 await/async 主要是关于释放线程来做其他事情而不是关于并行性。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM