簡介
Combine是Apple在2019年WWDC上推出的一個新框架。該框架提供了一個聲明性的Swift API,用於隨時間處理值。這些值可以表示多種異步事件。
Publisher協議聲明了一種可以隨時間傳遞一系列值的類型。Operators根據從upstream publishers接受到的值采取行動,並重新發布這些值。
在publishers鏈的末尾,Subscriber在接收元素時對其進行操作。Publisher僅在Subscriber明確請求時才會發出值。
通過采用Combine,通過集中事件處理代碼並消除嵌套閉包和基於約定的回調等麻煩的技術,使代碼更易於閱讀和維護。
Combine 是基於泛型實現的,是類型安全的。它可以無縫地接入已有的工程,用來處理現有的 Target/Action、Notification、KVO、callback/closure 以及各種異步網絡請求。
在 Combine 中,有幾個重要的組成部分:
發布者:Publiser 訂閱者:Subscriber 操作符:Operator
Publisher
在 Combine 中,Publisher 相當於RxSwift中的 Observable,並且可以通過組合變換(Operator)重新生成新的 Publisher。
public protocol Publisher { /// The kind of values published by this publisher. associatedtype Output /// The kind of errors this publisher might publish. /// /// Use `Never` if this `Publisher` does not publish errors. associatedtype Failure : Error /// This function is called to attach the specified `Subscriber` to this `Publisher` by `subscribe(_:)` /// /// - SeeAlso: `subscribe(_:)` /// - Parameters: /// - subscriber: The subscriber to attach to this `Publisher`. /// once attached it can begin to receive values. func receive<S>(subscriber: S) where S : Subscriber, Self.Failure == S.Failure, Self.Output == S.Input }
在 Publisher 的定義中,Output 代表數據流中輸出的值,值的更新可能是同步,也可能是異步,Failure 代表可能產生的錯誤,也就是說 Pubslier 最核心的是定義了值與可能的錯誤。Publisher 通過 receive(subscriber:) 用來接受訂閱,並且要求 Subscriber 的值和錯誤類型要一致來保證類型安全。
看一個例子:
let justPubliser = Just("Hello") justPubliser 會給每個訂閱者發送一個 "Hello" 消息,然后立即結束(這個數據流只包含一個值)。 Combine提供了一個 enum Publishers,包括: struct Empty : 一個從不發布任何值的publisher,並且可以選擇立即完成。 struct Fail : 立即使用指定錯誤終止的publisher。 struct Once: 只有一次向每個訂閱者發布輸出然后完成的publisher,或者在沒有生成任何元素的情況下立即失敗的publisher。 struct Optional : 如果可選值具有值,則publisher僅向每個訂閱者發布一次可選值。 struct Sequence : 發布給定元素序列的publisher。 struct Deferred : 在運行提供的閉包之前等待訂閱的發布者,以便為新訂閱者創建發布者。 ... Subscriber Subscriber相當於RxSwift中的Observer。 public protocol Subscriber : CustomCombineIdentifierConvertible { /// The kind of values this subscriber receives. associatedtype Input /// The kind of errors this subscriber might receive. /// /// Use `Never` if this `Subscriber` cannot receive errors. associatedtype Failure : Error /// Tells the subscriber that it has successfully subscribed to the publisher and may request items. /// /// Use the received `Subscription` to request items from the publisher. /// - Parameter subscription: A subscription that represents the connection between publisher and subscriber. func receive(subscription: Subscription) /// Tells the subscriber that the publisher has produced an element. /// /// - Parameter input: The published element. /// - Returns: A `Demand` instance indicating how many more elements the subcriber expects to receive. func receive(_ input: Self.Input) -> Subscribers.Demand /// Tells the subscriber that the publisher has completed publishing, either normally or with an error. /// /// - Parameter completion: A `Completion` case indicating whether publishing completed normally or with an error. func receive(completion: Subscribers.Completion<Self.Failure>) }
可以看出,Publisher 在自身狀態改變時,調用 Subscriber 的三個不同方法(receive(subscription), receive(_:Input), receive(completion:))來通知 Subscriber。
這里也可以看出,Publisher 發出的通知有三種類型:
Subscription:Subscriber 成功訂閱的消息,只會發送一次,取消訂閱會調用它的 Cancel 方法來釋放資源 Value(Subscriber 的 Input,Publisher 中的 Output):真正的數據,可能發送 0 次或多次 Completion:數據流終止的消息,包含兩種類型:.finished 和 .failure(Error),最多發送一次,一旦發送了終止消息,這個數據流就斷開了,當然有的數據流可能永遠沒有終止 大部分場景下我們主要關心的是后兩種消息,即數據流的更新和終止。