如果我有像
这样的方法Task<bool> LongProcessTaskAsync();
返回已启动的任务是否更好?
return Task<bool>.Factory.StartNew(() => { ... });
或仅return new Task<bool>(() => ...)
就个人而言,我更喜欢第一种方法,但我宁愿与其他API和库保持一致。
返回一个未启动的任务更合适吗?
答案 0 :(得分:16)
对于async / await方法,任务已经启动。 AFAIK,为基于任务的版本添加的所有BCL方法都返回已启动的任务。因为普通的消费者案例现在是这样的,所以有点奇怪:
var foo = await GetFooAsync();
[编辑]基于Stephen指出TAP指南涵盖了这一点(并且他已经包含了指南的链接),我将在第4页中包含相关位的引用(在基于任务的异步模式定义 - &gt;行为 - &gt;任务状态),我在关键部分周围添加了粗体+斜体。
任务状态
Task类为异步操作提供生命周期 该循环由TaskStatus枚举表示。为了 支持从任务和任务派生的类型的角落案例 以及从调度分离构造,Task类 公开一个Start方法。由其公共构造函数创建的任务是 被称为“冷”的任务,因为他们开始了他们的生命周期 非调度的TaskStatus.Created状态,直到Start 在这些实例上调用它们进行计划。 所有其他任务都以“热”状态开始其生命周期,这意味着 它们代表的异步操作已经启动 并且它们的TaskStatus是除Created之外的枚举值。
从TAP方法返回的所有任务都必须“热门”。 如果采用TAP方法 在内部使用Task的构造函数来实例化任务 返回时,TAP方法必须在之前调用Task对象上的Start 归还它。 TAP方法的消费者可以安全地假设 返回的任务是“热门”,不应该尝试在任何上面调用Start 从TAP方法返回的任务。 将在“热门”任务上调用Start 导致InvalidOperationException(此检查已处理 由Task类自动完成。
答案 1 :(得分:3)
詹姆斯曼宁正确回答。这是另一个角度:为什么有人想要一个未启动的任务?如果他这样做,他可以等待调用该方法。他本可以稍后给它打电话,或将它包裹在懒惰或未来的自己身上。几乎没有理由不返回已启动的任务。