函数与闭包
Trailing Closure、async 函数。
30 分钟
函数与闭包
Swift 函数是一等公民;闭包(Closure)可捕获上下文,是 SwiftUI 事件处理与异步编程的基础。对照 /roadmaps/swift-ui「函数与闭包」节点。
学习目标
- 定义带参数标签、默认值与可变参数的函数
- 理解闭包语法与 Trailing Closure
- 掌握
@escaping与捕获列表[weak self] - 编写
async函数并在 SwiftUI 中调用
核心概念
函数定义与参数
func formatDuration(minutes: Int, suffix: String = "分钟") -> String {
return "\(minutes) \(suffix)"
}
func sum(_ numbers: Int...) -> Int {
numbers.reduce(0, +)
}
// 多返回值(元组)
func parseLesson(_ raw: String) -> (id: Int, title: String)? {
let parts = raw.split(separator: "|")
guard parts.count == 2, let id = Int(parts[0]) else { return nil }
return (id, String(parts[1]))
}
外部参数名提升可读性:formatDuration(minutes: 35);_ 省略外部标签。
闭包与 Trailing Closure
var lessons = ["语法", "控制流", "闭包"]
// 完整闭包
let sorted = lessons.sorted(by: { (a, b) -> Bool in
a.count < b.count
})
// Trailing Closure:最后一个闭包参数可写在括号外
let sorted2 = lessons.sorted { $0.count < $1.count }
// SwiftUI 中常见
Button("排序") {
lessons.sort { $0.count < $1.count }
}
$0、$1 是闭包参数简写;SwiftUI 的 .onTapGesture { }、.task { } 均使用 Trailing Closure。
async 函数
struct Lesson: Decodable {
let id: Int
let title: String
}
func fetchLesson(id: Int) async throws -> Lesson {
try await Task.sleep(nanoseconds: 300_000_000)
return Lesson(id: id, title: "课时 \(id)")
}
struct LessonLoaderView: View {
@State private var lesson: Lesson?
@State private var isLoading = false
var body: some View {
VStack(spacing: 16) {
if isLoading {
ProgressView()
} else if let lesson {
Text(lesson.title).font(.title2)
}
Button("加载") {
Task {
isLoading = true
defer { isLoading = false }
lesson = try? await fetchLesson(id: 1)
}
}
}
.padding()
}
}
async throws 函数用 try await 调用;SwiftUI 中用 Task { } 启动异步任务, 修饰符在视图出现时自动执行。