You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

互斥取消Tasks:寻求更简洁的异步实现方案

更简洁的实现方案

你可以利用Swift的TaskGroup来实现这个逻辑,它天然支持并发任务的竞争场景,代码更简洁优雅,不需要手动管理两个任务的引用和互相取消的逻辑:

func startTest() async throws {
    Task { await test() }
    try await Task.sleep(nanoseconds: 1 * NSEC_PER_SEC)
    // comment out this next line to test the timeout
    NotificationCenter.default.post(name: .init("Test"), object: nil)
}

func test() async {
    await withTaskGroup(of: Void.self) { group in
        // 添加等待通知的任务
        group.addTask {
            for await _ in NotificationCenter.default
                .notifications(named: .init("Test"), object: nil)
                .prefix(1) {}
            print("Done waiting for the notification")
        }
        
        // 添加超时任务
        group.addTask {
            try? await Task.sleep(nanoseconds: 5 * NSEC_PER_SEC)
            print("I timed out and cancelled the notification task")
        }
        
        // 等待第一个完成的任务
        _ = await group.next()
        // 取消所有未完成的任务
        group.cancelAll()
    }
    
    print("finished!")
}

方案优势

  • 无需手动持有两个Task的引用,TaskGroup会自动管理所有子任务
  • group.next()会直接返回第一个完成的任务结果,天然实现"先完成者胜出"的逻辑
  • group.cancelAll()会自动取消所有未完成的子任务,不用手动调用单个任务的cancel()方法
  • 代码结构更紧凑,符合Swift并发框架的设计理念

如果需要处理任务的返回值或错误,只需要调整TaskGroup的泛型参数(比如of: Result<Void, Error>.self),并在next()后处理对应结果即可。

内容的提问来源于stack exchange,提问作者matt

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.11 11:11:22