为什么ContinueWith将Task作为参数传递

时间:2016-03-10 21:01:45

标签: .net task-parallel-library design-decisions

我有Task<T> t1。我想在Task t2完成后运行另一个t1。我选择使用.ContinueWith的{​​{1}}方法。

t1

除此之外,我不能这样做,因为void ThenFrob(Task<Frobber> t1) { t1.ContinueWith(frobber => frobber.Frob()) } 的Action参数是Task<T>而不是Task<T>本身。相反,我必须将传递给我的动作的参数的结果与它进行交互。

T

如果ContinueWith的意思是向链添加另一个动作,为什么语言设计者不会简单地传递上一个任务的结果?或者,在非通用任务的情况下,期望无参数动作?

1 个答案:

答案 0 :(得分:2)

当任务进入task.IsCompleted == true状态时,ContinueWith运行委托。不是当它进入task.IsCompleted == true && task.IsFaulted == false && task.IsCanceled == false状态时,抛出异常的任务或被取消的任务都会“完成”,但不会产生结果。

您可以通过TaskContinuationOptions传递重载,例如TaskContinuationOptions.OnlyOnRanToCompletion来获取您所描述的行为,但是对于单个枚举选项而言,Action<T>重载会更复杂因此,他们只使用Action<Task<T>>的一般重载,因此如果您正在执行OnlyOnRanToCompletion或正在执行OnlyOnFaulted,则可以使用相同的方法。

如果您使用AsyncState属性传递元数据,如果已完成的任务未传递给{{1},则完成任务的Task对象中仍然存在有用的信息除非你使用lambada表达式的变量捕获,否则你无法获得那些数据。