iOS 开发 — Swift (八) 闭包

闭包
与 OC 中的 Block 类似,闭包主要用于异步操作执行完成后的代码回调,网络访问结果以参数的形式传递给调用方

定义一个函数
//: 定义一个 sum 函数
func sum(num1 num1: Int, num2: Int) -> Int {
return num1 + num2
}
sum(num1: 10, num2: 30)

//: 在 Swift 中函数本身就可以当作参数被定义和传递
let mySum = sum
let result = mySum(num1: 20, num2: 30)
定义一个闭包
闭包 = { (行参) -> 返回值 in // 代码实现 }
in 用于区分函数定义和代码实现
//: 闭包 = { (行参) -> 返回值 in // 代码实现 }
let sumFunc = { (num1 x: Int, num2 y: Int) -> Int in
return x + y
}
sumFunc(num1: 10, num2: 20)
闭包格式小结
// 格式: let 闭包名: (形参) -> 返回类型 = { (形参1, 形参2, …) in 代码实现 }
// 说明: 使用形参列表,可以直接提供外部参数
//
// 格式: let 闭包名: (形参类型) -> 返回类型 = { (形参1, 形参2, …) in 代码实现 }
//
// 格式: { (外部参数1 形参1, 外部参数2 形参2, …) -> 返回类型 in 代码实现 }
// 说明: 使用外部参数会方便调用
//
// 格式: { (形参列表) -> 返回类型 in 代码实现 }
*简单的闭包,如果没有参数/返回值,则 参数/返回值/in 统统都可以省略
{ 代码实现 }
let demoFunc = {
print(“hello”)
}

闭包的基本使用
GCD 异步
模拟在后台线程加载数据
func loadData() {
dispatch_async(dispatch_get_global_queue(0, 0), { () -> Void in
print(“耗时操作 \(NSThread .currentThread())”)
})
}
尾随闭包,如果闭包是*后一个参数,可以用以下写法
注意上下两段代码,} 的位置
func loadData() {
dispatch_async(dispatch_get_global_queue(0, 0)) { () -> Void in
print(“耗时操作 \(NSThread .currentThread())”)
}
}
闭包的简写,如果闭包中没有参数和返回值,可以省略
func loadData() {
dispatch_async(dispatch_get_global_queue(0, 0)) {
print(“耗时操作 \(NSThread .currentThread())”)
}
}
自定义闭包参数,实现主线程回调
添加没有参数,没有返回值的闭包
override func viewDidLoad() {
super.viewDidLoad()

loadData {
print(“完成回调”)
}
}

// MARK: – 自定义闭包参数
func loadData(finished: ()->()) {

dispatch_async(dispatch_get_global_queue(0, 0)) {
print(“耗时操作 \(NSThread.currentThread())”)

dispatch_sync(dispatch_get_main_queue()) {
print(“主线程回调 \(NSThread.currentThread())”)

// 执行回调
finished()
}
}
}
添加回调参数
override func viewDidLoad() {
super.viewDidLoad()

loadData4 { (html) -> () in
print(html)
}
}

/// 加载数据
/// 完成回调 – 传入回调闭包,接收异步执行的结果
func loadData4(finished: (html: String) -> ()) {

dispatch_async(dispatch_get_global_queue(0, 0)) {
print(“加载数据 \(NSThread.currentThread())”)

dispatch_sync(dispatch_get_main_queue()) {
print(“完成回调 \(NSThread.currentThread())”)

finished(html: “<h1>hello world</h1>”)
}
}
}