【问题标题】:Difference between Thread, Task and async/await keywords [closed]线程、任务和异步/等待关键字之间的区别 [关闭]
【发布时间】:2019-06-08 20:20:27
【问题描述】:

最近几天我尝试学习 .NET 中的多任务处理。我对此没有什么疑问。 首先。我知道在 .NET 中存在名为“ThreadPool”的东西,所以如果我们使用 Thread 类创建新线程,我们会使用 ThreadPool 中的线程还是创建新线程?

任务库呢。在 msdn 中我们可以读到:“表示异步操作”。但是创建新线程和使用异步是两种不同的方式,对吧?那么如果我们使用任务库,我们会创建异步操作还是创建新线程?

如果是,那么我们应该何时使用 async/await 关键字? 以上方法的区别在哪里?

【问题讨论】:

  • 你混合了两个不同的概念:异步编程和多任务。
  • 你能描述一下吗?或者给我任何链接,我可以在哪里找到比较。
  • 抱歉,是用我的手机写的。这更像是这些是你应该寻找的东西建议。

标签: c# .net task-parallel-library async-await


【解决方案1】:

让我们试着打破每个问题:

所以如果我们使用 Thread 类创建新线程,我们会使用来自的线程 ThreadPool 还是新建一个?

ThreadPool 顾名思义,它是一个线程池。当您使用Thread 类时,您正在创建一个 线程,与ThreadPool 中存在的线程无关。

在 msdn 中我们可以读到:“表示异步操作。”但 创建新线程和使用异步是两种不同的方式, 对吧?

没错。执行异步操作并不意味着“创建一个新线程并在该线程上工作”。我的意思是,那是在并行中做事。异步操作通常在进程中require no extra threads,它们自然是异步的,一直到操作系统。

因此,如果我们使用任务库,我们会创建异步操作或创建新的 线程?

两者都可以:

  1. Promise 风格的任务 - 这些任务与 C# 5 中引入的 async-await 运算符很好地配合使用。它们代表不需要使用线程的异步操作。这些示例可以在各种 BCL 类中找到,例如 Stream 类、HttpClient 等。请注意,大多数执行 I/O 绑定操作的类都使用 promise 样式的任务。

  2. 使用Task.RunTask.Factory.StartNew。这将采用ThreadPool 线程并在内部执行提供的委托,除非您明确告诉它您希望它使用TaskCreationOptions.LongRunning 创建一个新线程。

如果是,那么我们应该何时使用 async/await 关键字?

async-await 与任何 awaitable 一起出现。 awaitable 是任何具有GetAwaiter 方法的类/结构,它返回实现INotifyCompletionICriticalNotifyCompletion 接口的类型。你可以阅读更多关于async-awaithere

【讨论】:

  • 这取决于TaskFactory 如何异步调用显式创建的任务。最常见的方式是使用线程池,但是还有其他类型的任务工厂……W
  • 另外,最好仅在需要对一个或多个异步操作进行建模时使用await,在完成后需要返回到特定线程上下文。大多数情况下,这意味着从 UI 线程调用异步操作时。
  • 我不会说“异步操作不需要线程”,因为它们的回调必须发生在线程上,即使它是原始线程;)但是如果您使用某种开始/等待或其他类型显式调用回调,那么这也发生在线程上。但是是的,实际操作可能不在线程上运行。
  • @Erik 我提到实际操作本身不会消耗线程。当然,一旦完成,它就必须调用 IOCP。请注意,我也说过 extra 线程。
猜你喜欢
  • 2015-05-08
  • 2011-03-16
  • 1970-01-01
  • 2021-11-07
  • 2021-12-28
  • 1970-01-01
  • 2015-07-13
  • 1970-01-01
相关资源
最近更新 更多