taskcanceledexception专门用于task被取消后的外部异常表示,当调用task.wait()或await task时,若task已取消,会抛出包含taskcanceledexception的aggregateexception;2. operationcanceledexception是更通用的取消异常,可在任何使用cancellationtoken的场景中抛出,通常在任务内部通过token.throwifcancellationrequested()触发,用于响应取消请求并执行清理;3. 两者关系为:task内部抛出operationcanceledexception后,task框架会将其封装为taskcanceledexception对外暴露,因此外部捕获的是taskcanceledexception,而内部处理取消逻辑时应捕获operationcanceledexception。

TaskCanceledException和OperationCanceledException都表示操作被取消,但它们的使用场景和上下文有所不同。TaskCanceledException专门用于Task取消的情况,而OperationCanceledException则更通用,可以用于任何支持取消操作的场景。
TaskCanceledException和OperationCanceledException的区别
TaskCanceledException和OperationCanceledException,虽然都代表取消操作,但细究起来,它们的适用范围和携带的信息略有不同。理解这些差异能帮助我们更精确地处理并发和异步编程中的取消逻辑。
TaskCanceledException主要用在Task相关的操作中。当一个Task被取消时,如果尝试访问Task的结果,就会抛出这个异常。它明确地表明了是Task自身被取消了,而不是其他原因导致操作失败。
例如,你有一个Task执行耗时操作,并允许用户取消它:
CancellationTokenSource cts = new CancellationTokenSource();
CancellationToken token = cts.Token;
Task task = Task.Run(() => {
for (int i = 0; i < 100; i++) {
if (token.IsCancellationRequested) {
token.ThrowIfCancellationRequested(); // 抛出 OperationCanceledException
}
Thread.Sleep(100);
Console.WriteLine($"Task running: {i}");
}
}, token);
cts.CancelAfter(2000); // 2秒后取消Task
try {
task.Wait(); // 如果Task被取消,这里会抛出 AggregateException,包含 TaskCanceledException
} catch (AggregateException ae) {
foreach (var e in ae.InnerExceptions) {
if (e is TaskCanceledException) {
Console.WriteLine("Task was cancelled.");
} else {
Console.WriteLine($"Exception: {e.GetType()}");
}
}
}在这个例子中,
token.ThrowIfCancellationRequested()
OperationCanceledException
task.Wait()
AggregateException
TaskCanceledException
TaskCanceledException
OperationCanceledException则是一个更通用的异常,用于表示任何操作因为取消而被中断。它不仅仅局限于Task,可以用于任何支持取消令牌的场景。
继续上面的例子,实际上我们在Task内部抛出的就是
OperationCanceledException
CancellationTokenSource cts = new CancellationTokenSource();
CancellationToken token = cts.Token;
Task task = Task.Run(() => {
try {
for (int i = 0; i < 100; i++) {
if (token.IsCancellationRequested) {
token.ThrowIfCancellationRequested(); // 抛出 OperationCanceledException
}
Thread.Sleep(100);
Console.WriteLine($"Task running: {i}");
}
} catch (OperationCanceledException) {
Console.WriteLine("Operation was cancelled inside the task.");
}
}, token);
cts.CancelAfter(2000); // 2秒后取消Task
try {
task.Wait();
} catch (AggregateException ae) {
foreach (var e in ae.InnerExceptions) {
if (e is TaskCanceledException) {
Console.WriteLine("Task was cancelled.");
} else {
Console.WriteLine($"Exception: {e.GetType()}");
}
}
}在这个修改后的例子中,我们在Task内部捕获了
OperationCanceledException
task.Wait()
TaskCanceledException
实际上,在Task内部,你通常会使用
CancellationToken.ThrowIfCancellationRequested()
OperationCanceledException
TaskCanceledException
虽然两者都表示取消,但
TaskCanceledException
OperationCanceledException
以上就是TaskCanceledException和OperationCanceledException有什么区别?的详细内容,更多请关注php中文网其它相关文章!
每个人都需要一台速度更快、更稳定的 PC。随着时间的推移,垃圾文件、旧注册表数据和不必要的后台进程会占用资源并降低性能。幸运的是,许多工具可以让 Windows 保持平稳运行。
Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号