Task 很优雅的取消方式是什么?C# 里面。

C# 里取消 Task 的正规做法是协作式取消:调用方拿 `CancellationTokenSource` 发出取消,任务内部用 `CancellationToken` 在安全的检查点自己停下来。不要用 `Thread.Abort`,也不要靠 `Dispose` 任务来取消。

怎么写

调用方创建取消源,把 Token 传进任务,需要停的时候调用 `Cancel()`,然后仍然 `await` 这个任务,让它做完收尾。

```csharp

using var cts = new CancellationTokenSource();

try

{

await RunAsync(cts.Token);

}

catch (OperationCanceledException)

{

// 这是取消,不是故障

}

void Stop() => cts.Cancel();

async Task RunAsync(CancellationToken ct)

{

while (true)

{

ct.ThrowIfCancellationRequested();

await DoOneStepAsync(ct); // 支持 Token 的 API 把 Token 继续传下去

await Task.Delay(10, ct);

}

}

```

`ThrowIfCancellationRequested()` 会抛出 `OperationCanceledException`。捕获它表示「被人停了」;别的异常才是失败。取消之后不要把流程记成成功。

为什么说它优雅

`Cancel()` 只是把标记设为已取消,不会把线程掐死。任务跑到下一次检查 Token 的地方才停,所以不会停在写到一半的串口帧或运动指令中间。

支持 Token 的 API 会自己停:`Task.Delay`、`ReadAsync`、`WaitAsync`、`Task.Run` 的重载。Token 要一路传到最底层,传断了,底层仍会把当前这次 IO 做完。

超时和停止按钮可以合成一个 Token:

```csharp

using var stopCts = new CancellationTokenSource();

using var timeoutCts = new CancellationTokenSource(TimeSpan.FromSeconds(30));

using var linked = CancellationTokenSource.CreateLinkedTokenSource(

stopCts.Token, timeoutCts.Token);

await MoveAndWaitAsync(linked.Token);

```

任一来源取消,任务都会看到。`CancelAfter` 则是同一个源上的超时。

收尾不要写在 `catch` 里碰运气。用 `finally`,或者 `token.Register(() => StopAxis())`,保证取消时能发减速停。`Register` 的回调可能跑在任意线程上,里面不要动 UI 控件。

上位机里怎么用

自动流程的等待循环带着 Token。停止按钮调用 `Cancel()`。通信线程在下一次检查时看到取消,再调用 `dmc_stop` 或写 PLC 停机位,然后抛出取消异常,状态机进入「已停止」。不要在 UI 线程里 `while` 等运动完成,也不要 `Abort` 那条正在调运动卡的线程。

相关推荐
FRing031 小时前
JavaScript入门到精通二十八(forEach遍历、创建对象的三种方式、构造函数、new实例化执行过程、实例成员和静态成员)
开发语言·前端·javascript
1024奇点2 小时前
【仓颉语言入门 · 第二篇 第 15 课】
开发语言·数据库·ide·开源
独隅2 小时前
Claude 高效使用指南深度评测
java·开发语言·claude·claude code
Agent世界2 小时前
千问Go上线我的应用:一句话生成可部署 AI 软件的技术拆解
开发语言·人工智能·golang·ai智能体
布莱克6052 小时前
C++ 中 unordered_set 与 unordered_map 有什么不同?一篇讲透
开发语言·c++·哈希
外收内放2 小时前
FastAPI猜字谜实战(6):日志与异常
开发语言·python·学习·fastapi
垆边人似月.2 小时前
预处理与参数调优(让识别率从“能看”到“可用”)
开发语言·python·自然语言处理
泡泡糖的中文规格书2 小时前
HDLbits 2.2 学习笔记 · 多路复用器
java·开发语言
John_Hui2 小时前
第 3 篇:配置 JDK 17 环境
java·开发语言·ubuntu