RxJS 和 數據驅動

數據驅動(data-driven) 是指將傳遞的數據和行為進行分離。這也是為什么RxJS能夠以相同的范式來處理不同類型的數據源(比如數組,字符串,事件,AJAX請求等等)的核心原理。

  • 以數據作為中心,將數據從行為系統中分離出來,用數據去驅動業務
  • 沒有數據,行為將不起作用,數據給行為帶來升級,行為響應數據的變化,而不是等待數據的到來
  • 流(stream)只是一個傳遞過程,如果沒有用戶訂閱,或者數據傳遞進來,流將保存閑置狀態
#1 stream如果沒有被訂閱將保持閑置狀態.jpg

數據生產者 producers

數據的產生有不同的原因,這樣造成數據源的來源有很多種情況。

  • 生產者有各種各樣的形態和大小, Event Emitter 就是比較常見的一種生產者,它們用于響應鼠標點擊或者網絡請求,同時他們也是基于時間的數據源
  • 當處理不同類型的數據源,我們應當自然會想到使用不同類型的方式來處理。不如 event emitters 需要使用命名event handlers 來處理,Promises 需要一個連續傳遞的 thenable 函數來處理; setTimeout需要回調函數來處理; Arrays 需要通過循環來迭代數據

但是Rx對不同類型的數據進行了包裝處理,這樣我們可以以相同的范式來處理不同類型的數據源,也就是說

不同類型的數據源在事件驅動(或流驅動)的棱鏡下觀察都是一樣的,
就好比Rx.Observable 是一個錘子,把其余所有的數據類型當作釘子

識別不同類型的數據源

數據源廣義的可以分為以下幾類:

  • Emitted Data
  • Static Data
  • Generated Data

1.Emitted Data

發生數據是一種外部與系統交互產生的結果。可以來自與用戶交互,比如點擊鼠標,也可以是系統事件,比如讀取文件。

比如你請求數據,未來某個時間點,你接收到數據,對于這種情況, Promises 可能是一個好的解決方案。

2.static data

靜態數據已經存在或者顯示在系統(內存)中,比如 array ,string。人工的單元測試數據就劃分到這一類型數據中。

3.Generated data

產生的數據是指間隔的或最終產生的數據,比如時鐘每小時都會報時。

比如無限產生的數據,不可能將其全部存儲在內存中,值應當動態的被創建和產生給需要的使用者。

數據類型的劃分

根據以下2個維度可以將數據劃分為4類:

  • 值的多少: 單值(比如數字), 多值(比如數組)
  • 數據的處理方式: 同步的, 還是異步的
數據類型的劃分.jpg

1.single-value && synchronous

這是最簡單的數據類型,比如數字,一個對象,我們可以通過 Rx.Observable.of 將其轉換為一個 Obserable類型。

但是一般處理簡單類型的數據使用Observable,有點殺雞用牛刀的味道,一般只有我們希望將簡單類型的值和其它類型的流整合在一起時,才使用Obserable

2.multi-value && synchronous

我們可以將單值集合起來形成集合,主要是數組類型。

我們可以使用 Rx.Obserable.from 將集合類型轉換為Obserable類型

3.single-value && asynchronous

對于異步的情況,正是RxJS大放異彩的地方

對于異步的情況,我們只能保證到嗎在未來某個時間被處理,因此,后面的代碼塊不能依賴前面代碼塊的執行。

對于單值異步的情況,使用 Promises 進行處理最好了,在RxJS中可以使用 Rx.Observable.fromPromise() 將promises轉換為Observable類型。

Rx.Observable.fromPromise($.ajax('/data'))

4. multi-value && aynchronous

這種類型的數據一般時間會作為數據來源的因子。比如DOM事件,不知道未來什么時候會產生。

對這種數據的處理我們需要 混合迭代器和promise模式,通常的處理方式是使用 EventEmitter 進行處理。

RxJS在javascript原有的EventEmitter的基礎上對其進行了改進。可以使用 Rx.Observable.fromEvent() 將EventEmitter 轉換為Observbale類型

PUSH-BASED && PULL-BASE MODEL

迭代器使用的 pull-based 模型, 而RXJS使用的是 push-based模型。

#3數據推送和數據拉取模型.jpg
  • pull-based 對下面情況是非常擁有的: 當我們知道一個字能從計算后立即返回時。對于不知道值什么時候返回或者有沒有值返回的情形,pull-based模型就失效了,比如鼠標點擊,使用者是不知道下一次點擊事件什么時候反生,或者發不發生
  • push-based模式中,生產者負責創建下一個數據,消費者只需要監聽新的事件即可
#3-1 push-based model.jpg

Observable && Observer

被觀察者和觀察者

  • 業務邏輯,比如值如何產生,怎么被發送歸屬于Observable,而所有的渲染細節,是否使用插件什么的處理邏輯歸屬于observer中的調度者
  • 要記住,無限事件發送,比如DO事件,將不會觸發 complete() 方法,因此,取消訂閱取決于使用者,可以采取手動取消訂閱或者自動取消訂閱機制
#4被觀察者和觀察者.jpg

Observable 基本api

被觀察者本質上一個函數

下面用簡單的方式來描述observable

const observable = events => { // 時間隊列
    const INTERVAL = 1 * 1000;
    let schedulerid;

    return { // 返回一個包含 'subscribe' 方法的對象
        subscribe: oberver => {  // 接收 observer 對象作為參數
            schedulerid = setInterval(() => {
                if (events.length === 0) { // 如果沒有時間處理了
                    observer.complete();
                    clearInterval(schedulerid);
                    schedulerid = undefined;
                } else { // 如果有事件反生, 使用 observer.next()方法進行處理
                    observer.next(events.shift());
                }
            }, INTERVAL);

            return {
                unsubscribe: () => { // subscribe 方法返回一個unsubscribe 方法用于取消訂閱
                    if (schedulerid) {
                        clearInterval(schedulerid);
                    }
                }
            };
        }
    }
}
#4-1被觀察者和觀察者.jpg

總結

主要將了以下幾個方面

  • RxJS采用了數據驅動的方式,數據和業務邏輯分離
  • RxJs對javascript的EventEmitter進行了改進,使其可以對事件進行推送
  • Push-based 和 Pull-based 方式的差異
  • 根據值的多少和處理方式2個維度,將數據源劃分為4類
  • 簡單Observable apis的介紹
    • Rx.Observable.of()
    • Rx.Observable.from()
    • Rx.Observable.fromPromise()
    • Rx.Observable.fromEvent()
  • Observable 和 Observer 之間的關系簡單介紹
最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容

  • 一.背景介紹 Rx(Reactive Extension -- 響應式擴展 http://reactivex.io...
    愛上Shu的小刺猬閱讀 2,094評論 1 3
  • 介紹 RxJS是一個異步編程的庫,同時它通過observable序列來實現基于事件的編程。它提供了一個核心的類型:...
    泓滎閱讀 16,639評論 0 12
  • 本文章內部分圖片資源來自RayWenderlich.com 本文結合自己的理解來總結介紹一下RxSwift最基本的...
    FKSky閱讀 2,924評論 4 14
  • Spring Cloud為開發人員提供了快速構建分布式系統中一些常見模式的工具(例如配置管理,服務發現,斷路器,智...
    卡卡羅2017閱讀 134,923評論 18 139
  • 關于Rxjs的現狀 鑒于響應式編程近幾年才開始真正流行,而且響應式的理念也并不是在所有領域都深得人心,對于不是特別...
    吧啦啦小湯圓閱讀 2,939評論 0 7