The primary principle of Delegate

Delegate 原理浅析

B 的一个方法运行到某处,需要把自己的一个值告诉 A,并且做一定处理

怎么来实现呢?

首先 B 要知道自己去告诉谁,然后再调用 A.aFunc()

我知道想知道原理的不想看代码,尽量简化了

A, B 类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
A.swift
class A {
func aFunc(b:B) {
println(b.value)
}
}

B.swift
class B {
var value = 0
func bFunc () {
value = 213 // value 有变化,想通知 A 执行 aFunc()
a.aFunc(b) // 错误
}
}

上面是不行的,为啥呢?
因为 b 里面并没有 a,如果直接把 A 传进去,就要修改 B 的代码,也就丢失了封装

我们看下 Delegate 怎么实现这种机制的

Delegate

既然是 B 要往外发送消息,就先从 B 下手:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
A.swift
class A {
func aFunc(b:B) {
println(b.value)
}
}

b.swift
protocol BDelegate {
func aFunc(b:B) // 1. 把 A 的 aFunc 声明成 BDelegate 的一个方法
}

class B {
var delegate:BDelegate? // 2. 声明一个 BDelegate 类型的 delegate 变量
var value = 0
func bFunc () {
value = 213
delegate?.aFunc(self) // 3. 把自己 b,作为参数,调用 aFunc()
}
}

做了 1、2、3 后,还是不行,为啥呢?

因为 A 不知道 B 进行了委托,两者没关联起来

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
a.swift
class A: BDelegate { // 1. BDelegate
func aFunc(b:B) {
b.delegate = self // 2. 把 b 的 delegate 变量设置成 self,也就是 a
println(b.value)
}
}

b.swift
protocol BDelegate {
func aFunc(b:B)
}

class B {
var delegate:BDelegate?
var value = 0

func bFunc () {
value = 213
delegate?.aFunc(self) // 3. 这下看懂了吧?delegate?.aFunc(self) 等价于 a.aFunc(b)
}
}

main.swift
let b = B()
let a = A()
a.aFunc(b)
b.bFunc()

// 这个可以在 Playground 里看结果了

大功告成

回想下常见的代码,比如:

1
2
3
4
5
mScrollView.delegate = self
...
class MYScrollView : UIScrollView, UIScrollViewDelegate {
...
func scrollViewDidEndDecelerating(scrollView: UIScrollView) {

是不是有种豁然开朗的感觉?

过两天说说 SELBlock


感觉还是木说清楚呢,有不清楚的地方,欢迎留言探讨哈~~~