iOS中NotificationCenter观察者模式为何无法触发SecondVC的回调?
通知触发失效问题定位&修复
核心bug来源
结合你写的Observer通知实现逻辑,SecondVC收不到广播的问题,全部和NotificationCenter的运行规则直接相关,高频原因集中在三点:
- SecondVC未执行观察者注册代码
你把通知注册逻辑写在SecondVC的viewDidLoad方法里,这个方法只有当SecondVC的视图被真正加载、生命周期走到对应节点才会触发。如果发广播时,SecondVC从来没被实例化、根本没走到addObserver那行代码,它就没在通知中心登记过,自然收不到任何广播。
通知中心只会响应明确发起的注册请求,类里写了注册代码但没实际执行到的话,效果和没写完全一样。 - 广播发送时机早于注册完成时间
NSNotificationCenter是纯实时广播机制,不会留存历史通知给后续注册的观察者。如果还没进入SecondVC、SecondVC还没完成注册时,你就已经在第一个VC上点了按钮发广播,哪怕之后再进入SecondVC,之前发过的通知也不会补发,自然看不到响应。 - 通知触发时UI控件未初始化
就算SecondVC已经完成注册,如果通知触发时它的视图还没加载完成,你代码里的mySecondLabel这个IBOutlet还是nil状态,这时候执行mySecondLabel.text = "xxx"的赋值操作不会有任何界面变化——对nil对象发setter消息在运行时会被静默忽略。
对应修复方案
- 把观察者注册逻辑从
viewDidLoad挪到SecondVC的初始化方法(init(coder:)/init(nibName:bundle:)),只要SecondVC实例一创建就立刻完成注册,不要等视图加载。 - 调整广播发送时机:确保所有需要接收通知的观察者都完成注册之后,再调用
post方法发广播。 - 在通知响应方法里加视图加载状态判断,确认IBOutlet已经完成连线后,再执行UI更新操作,避免给空控件赋值。
补充说明:你代码里
addObserver时传object: nil是正确写法,代表接收所有带对应通知名的广播,不会因为post时传了self作为object导致接收失败,这个部分没有bug。
内容的提问来源于stack exchange,提问作者Marlhex
相关产品推荐
相关产品推荐

