【问题标题】:Use await for background threads or not?是否将 await 用于后台线程?
【发布时间】:2017-08-20 02:32:10
【问题描述】:

我目前正在研究 async/await 关键字,并遇到了以下问题:When correctly use Task.Run and when just async-awaitAsync/Await vs Threads

然而,即使是第二个链接也没有回答我的问题,即何时简单地使用

Task.Run(...)

await Task.Run(...)

是情景还是使用 await 可以获得什么(从而返回给调用者)?

【问题讨论】:

  • 像任何其他使用 Task 一样,不等待将导致任务被触发并立即继续执行当前方法,而等待将返回一个任务并将方法的其余部分连接为继续(有效地停止当前方法的执行,直到任务完成)。你想达到什么目的?
  • @AntP 由于我是这些关键字的新手,我只是想了解使用 await 来创建后台线程是否被认为是一种好习惯,而不是直接启动它们,或者如果使用 await Task.Run(...) 更具情境性,然后,我应该在什么情况下这样做?
  • 这两件事会产生不同的行为,所以这是有条件的——如果你想返回一个不完整的Task,可以在堆栈的更上层等待(例如附加额外的延续,处理失败.. .),您将需要等待(或返回)Task.Run 返回的任务。如果您想启动任务并忘记它,您不想等待它。
  • @AntP 对,“如果你想启动任务并忘记它,你不想等待它”现在更有意义

标签: c# .net asynchronous async-await


【解决方案1】:

代码Task.Run(...)(在两个示例中)将一个委托发送到线程池并返回一个包含该委托结果的任务。这些“结果”可以是实际的返回值,也可以是异常。您可以使用返回的任务来检测结果何时可用(即委托何时完成)。

因此,如果任何为真,您应该使用Task

  • 您需要检测操作何时完成并以某种方式响应。
  • 您需要知道操作是否成功完成。
  • 您需要处理操作中的异常。
  • 您需要对操作的返回值做一些事情。

如果您的调用代码需要执行上述任何操作,请使用await

await Task.Run(...);

对于长时间运行的后台任务,有时您想执行这些操作(例如,检测异常),但您不想立即执行;在这种情况下,只需将 Taskawait 保存在应用程序的其他位置即可:

this.myBackgroundTask = Task.Run(...);

如果您不需要上述任何一项,那么您可以进行“一劳永逸”,如下所示:

var _ = Task.Run(...); // or just "Task.Run(...);"

请注意,真正的“一劳永逸”应用程序极为罕见。它的字面意思是“运行这段代码,但我不在乎它是否完成、何时完成或是否成功”。

【讨论】:

    【解决方案2】:

    您可以使用 Task.Run() 来处理具有触发和忘记类型的逻辑,类似于在有人订阅它们时调用事件。您可以将其用于记录、通知等。

    如果您依赖方法中执行的结果或操作,则需要使用 await Task.Run(),因为它会暂停当前执行,直到您的任务完成。

    【讨论】:

      猜你喜欢
      • 2023-03-09
      • 2020-11-19
      • 2020-07-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-01-15
      相关资源
      最近更新 更多