使用 TaskGroup 实现并行
使用 withTaskGroup 运行并行子任务,在结果到达时逐一处理,并使用会抛出错误的变体处理失败。
使用 TaskGroup 实现并行 是 CoddyKit 上的免费 Swift Academy 课时。 这是第 1 节课,共 3 节。 你可以在下方免费阅读本课时的完整内容 — 然后在浏览器中使用内置代码编辑器和全天候 AI 导师进行实践。 这是 Swift Academy 学习路径的一部分,你的进度在网页和 CoddyKit 应用中同步。 Swift Academy 课程共包含 3 节课。
为什么使用 TaskGroup?
TaskGroup会并行启动许多子任务,并安全地收集结果。任务组只有在所有子任务完成后才会结束。
- 使用group.addTask启动
- 使用异步遍历消费结果
- 使用可抛出错误的变体传播错误
启动并收集
使用addTask启动子任务,并通过for await在结果到达时遍历它们。
func work(_ n: Int) async -> Int {
try? await Task.sleep(nanoseconds: UInt64(50_000_000 * n)) // simulate delay
return n * n
}
Task {
let result = await withTaskGroup(of: Int.self) { group in
for i in 1...4 {
group.addTask { await work(i) } // spawn child
}
var sum = 0
for await value in group { // values as they finish
sum += value
}
return sum
}
print("sum =", result) // 1^2+2^2+3^2+4^2 = 30
}汇总结果
任务组是一个结果异步序列;您可以使用reduce或循环来构建单个返回值。
func sumSquares(_ n: Int) async -> Int {
await withTaskGroup(of: Int.self) { group in
(1...n).forEach { i in
group.addTask { await work(i) }
}
return await group.reduce(0, +) // reduce over async sequence
}
}
Task {
print(await sumSquares(5)) // 55
}可抛出错误的任务组
使用withThrowingTaskGroup传播第一个错误;取消剩余子任务以停止无效工作。
enum CalcError: Error { case boom(Int) }
func risky(_ i: Int) async throws -> Int {
try await Task.sleep(nanoseconds: 30_000_000)
if i == 3 { throw CalcError.boom(i) }
return i
}
Task {
do {
let total = try await withThrowingTaskGroup(of: Int.self) { group in
for i in 1...5 { group.addTask { try await risky(i) } }
var sum = 0
do {
for try await v in group { sum += v }
return sum
} catch {
// Cancel remaining children on error
group.cancelAll()
throw error
}
}
print("total:", total)
} catch {
print("failed:", error) // boom(3)
}
}取消子任务
调用group.cancelAll()请求取消。子任务应检查Task.isCancelled(或Task.checkCancellation())并快速退出。
func slow(_ i: Int) async -> Int {
for _ in 0..<5 {
if Task.isCancelled { return -1 } // observe cancellation cooperatively
try? await Task.sleep(nanoseconds: 20_000_000)
}
return i * 10
}
Task {
let value = await withTaskGroup(of: Int.self) { group in
for i in 1...3 { group.addTask { await slow(i) } }
// cancel quickly (e.g., user navigated away)
group.cancelAll()
// Still need to drain results; cancelled children should exit fast
var out = 0
for await v in group { out += v }
return out
}
print("after cancel, collected:", value)
}指南
提示:
- 当子任务数量动态变化时,优先使用任务组。
- 使用可抛出错误的变体以实现快速失败。
- 即使取消后,也始终耗尽任务组(循环处理结果)。
- 让子任务保持小型,以便及时响应取消。
结构化汇合语义
快速检查:withTaskGroup能保证什么?
回顾
回顾:使用withTaskGroup启动并行工作,在结果到达时遍历它们,并优先使用可抛出错误的变体来快速失败并取消其余工作。
常见问题解答
「使用 TaskGroup 实现并行」课时是免费的吗?
是的 — 「使用 TaskGroup 实现并行」的完整文本可在网页上免费阅读。要进行交互式练习(内置代码编辑器和全天候 AI 导师)并解锁 Swift Academy 课程的其余内容,请升级到 CoddyKit PRO。 Swift Academy 课程共包含 3 节课。
「使用 TaskGroup 实现并行」这节课中我会学到什么?
使用 withTaskGroup 运行并行子任务,在结果到达时逐一处理,并使用会抛出错误的变体处理失败。 你通过在浏览器中直接运行的动手代码来练习 Swift Academy,全天候 AI 导师会在你学习这节课的过程中回答你的问题。
学习 Swift Academy 需要有经验吗?
无需任何先前经验。CoddyKit 上的 Swift Academy 课程适合初学者到高级学习者,你可以从这里开始或从头开始,按照自己的节奏学习。 这是第 1 节课,共 3 节。
「使用 TaskGroup 实现并行」课时需要多长时间?
大多数 CoddyKit 课程大约需要 5–10 分钟。每节课都很精短且互动,所以你能稳步进步,并在网页和应用中从离开的地方继续。
我能在这节 Swift Academy 课中编写并运行代码吗?
能。每节 Swift Academy 课都包含内置代码编辑器,你可以在浏览器中直接编写并运行真实代码,并获得即时 AI 反馈 — 无需本地设置。
此课程中的所有课时
- 使用 TaskGroup 实现并行
- 参与者与数据隔离、nonisolated
- Sendable 与线程安全检查