NSNotificationCenter
這是個單例類,負責管理通知的創建和發送,屬於最核心的類了。而NSNotificationCenter
類主要負責三件事
- 添加通知
- 發送通知
- 移除通知
NSNotificationQueue
功能介紹
通知隊列,用於異步發送消息,這個異步並不是開啓線程,而是把通知存到雙向鏈表實現的隊列裏面,等待某個時機觸發時調用NSNotificationCenter
的發送接口進行發送通知,這麼看NSNotificationQueue
最終還是調用NSNotificationCenter
進行消息的分發
另外NSNotificationQueue
是依賴runloop
的,所以如果線程的runloop
未開啓則無效,至於爲什麼依賴runloop
下面會解釋
NSNotificationQueue
主要做了兩件事:
- 添加通知到隊列
- 刪除通知
NSNotificationCenter
是同步發送的,而這裏介紹關於NSNotificationQueue
的異步發送,從線程的角度看並不是真正的異步發送,或可稱爲延時發送,它是利用了runloop
的時機來觸發的
對於NSNotificationQueue
總結如下
- 依賴
runloop
,所以如果在其他子線程使用NSNotificationQueue
,需要開啓runloop - 最終還是通過
NSNotificationCenter
進行發送通知,所以這個角度講它還是同步的 - 所謂異步,指的是非實時發送而是在合適的時機發送,並沒有開啓異步線程
主線程響應通知
異步線程發送通知則響應函數也是在異步線程,如果執行UI刷新相關的話就會出問題,那麼如何保證在主線程響應通知呢?
其實也是比較常見的問題了,基本上解決方式如下幾種:
- 使用
addObserverForName: object: queue: usingBlock
方法註冊通知,指定在mainqueue
上響應block
- 在主線程註冊一個
machPort
,它是用來做線程通信的,當在異步線程收到通知,然後給machPort
發送消息,這樣肯定是在主線程處理的
RunLoop是一個接收處理異步消息事件的循環,一個循環中:等待事件發生,然後將這個事件送到能處理它的地方。
runLoop實際上是一個對象,這個對象在循環中用來處理程序運行過程中出現的各種事件(比如說觸摸事件、UI刷新事件、定時器事件、Selector事件)和消息,從而保持程序的持續運行;而且在沒有事件處理的時候,會進入睡眠模式,從而節省CPU資源,提高程序性能。