天天看點

rxjs pipe和filter組合的一個實際例子的單步調試

源代碼:

const source$ = range(0, 10);      
rxjs pipe和filter組合的一個實際例子的單步調試

range(0,10)傳回一個新的Observable,但是不會立即執行,直到遇到subscribe調用為止:

rxjs pipe和filter組合的一個實際例子的單步調試

下圖高亮的這段代碼,在Observable.subscribe後會執行:

rxjs pipe和filter組合的一個實際例子的單步調試

注冊到Observable的_subscribe裡:

rxjs pipe和filter組合的一個實際例子的單步調試
ngOnInit(): void {
    console.log('before ngOnInit');
    const source$ = range(0, 10);


    source$.pipe(
      filter((x, index) => {
        console.log('inside filter!: ' + x + ' index: ' + index); 
        return x % 2 === 0 }),
      map( x => { 
        console.log('inside map: ' + x);
        return (x + x); }
        ),
      // scan((acc, x) => acc + x, 0)
      scan(this.accumulator)
    )
    .subscribe(x => console.log('result: ' + x));
  }      

pipe調用的參數傳入的是filter, map和scan三個操作的結果,是以首先執行filter:

位于operators目錄裡:

rxjs pipe和filter組合的一個實際例子的單步調試

filter操作接收的參數predicate, 類型是一個函數,該函數接收x和index兩個參數,傳回boolean類型,這就是所謂的filter-過濾器。filter操作傳回一個新的函數,該函數接收一個新的輸入source,對source調用lift操作,施加predicate操作。

rxjs pipe和filter組合的一個實際例子的單步調試

然後執行pipe操作:

rxjs pipe和filter組合的一個實際例子的單步調試

pipe的輸入參數就是filter調用的傳回結果:

rxjs pipe和filter組合的一個實際例子的單步調試

pipeFromArray傳回的就是包裹了filter操作的filterOperatorFunction:

rxjs pipe和filter組合的一個實際例子的單步調試

進入之前filter調用傳回的新函數:

rxjs pipe和filter組合的一個實際例子的單步調試

這個source應該是range(0,10)傳回的Observable:

rxjs pipe和filter組合的一個實際例子的單步調試

對原始Observable對象調用filter傳回的predicate操作:

rxjs pipe和filter組合的一個實際例子的單步調試

life操作内部建立了一個Observable對象,source是原始Observable對象,operator就是filter對應的predicate.

Observable遇到subscribe方法才會真正地執行Observable内部的方法:

rxjs pipe和filter組合的一個實際例子的單步調試

建立一個subscriber,第一個輸入參數nextOrObserver就是應用程式裡subscribe方法裡傳入的箭頭函數:

rxjs pipe和filter組合的一個實際例子的單步調試

subscriber是subscription的子類:

rxjs pipe和filter組合的一個實際例子的單步調試
rxjs pipe和filter組合的一個實際例子的單步調試

next就是應用程式傳入的箭頭函數:

rxjs pipe和filter組合的一個實際例子的單步調試

注意這裡,sink已經準備調用operator了。operator就是filter操作:

rxjs pipe和filter組合的一個實際例子的單步調試

進入filter操作:

rxjs pipe和filter組合的一個實際例子的單步調試

開始執行subscribe:

rxjs pipe和filter組合的一個實際例子的單步調試

執行complete的條件:

rxjs pipe和filter組合的一個實際例子的單步調試

調用next:

rxjs pipe和filter組合的一個實際例子的單步調試
rxjs pipe和filter組合的一個實際例子的單步調試

由此可見,range Observable裡包含的值,逐一調用filter:

rxjs pipe和filter組合的一個實際例子的單步調試

如果filter傳回true,繼續調用下一個Observable對象:

rxjs pipe和filter組合的一個實際例子的單步調試

這裡最終就調用應用程式裡傳入的subscribe方法了:

rxjs pipe和filter組合的一個實際例子的單步調試

range = 0的value已經執行完畢了,下面進行range1:

rxjs pipe和filter組合的一個實際例子的單步調試
rxjs pipe和filter組合的一個實際例子的單步調試

因為range = 1時filter傳回false,是以Observable鍊式執行到這裡就中斷了:

rxjs pipe和filter組合的一個實際例子的單步調試

range = 2,下面的原理類似,不重複介紹了。

繼續閱讀