RxJava2流程分析2-事件流

概述

RxJava是一個用於使用可觀察的序列組合異步和基於事件的程序的庫,其主要是用於異步的、可線程切換的、可觀察序列事件,那麼這個事件序列倒是是什麼樣的?(注:RxJava版本:2.2.7)

目的

  1. 事件序列是怎麼形成的
  2. 事件的流向

分析

分析的代碼

Observable.create(new ObservableOnSubscribe<Integer>() {
        @Override
        public void subscribe(ObservableEmitter<Integer> emitter) throws Exception {
            Log.d("RxJava:", "subscribe:");
            emitter.onNext(1);
            emitter.onComplete();
        }
    }).map(new Function<Integer, String>() {
        @Override
        public String apply(Integer integer) throws Exception {
            Log.d("RxJava:", "map1:");
            return integer.toString();
        }
    }).map(new Function<String, String>() {
        @Override
        public String apply(String s) throws Exception {
            Log.d("RxJava:", "map2:");
            return s;
        }
    }).subscribe(new Observer<String>() {
        @Override
        public void onSubscribe(Disposable d) {

        }
        @Override
        public void onNext(String s) {
            Log.d("RxJava:", "onNext:");
        }
        @Override
        public void onError(Throwable e) {

        }
        @Override
        public void onComplete() {

        }
    });

運行結果:
2020-01-07 17:17:51.527 20237-20237/com.wkkun.litho D/RxJava:: subscribe:
2020-01-07 17:17:51.527 20237-20237/com.wkkun.litho D/RxJava:: map1:
2020-01-07 17:17:51.527 20237-20237/com.wkkun.litho D/RxJava:: map2:
2020-01-07 17:17:51.527 20237-20237/com.wkkun.litho D/RxJava:: onNext:

首先分析操作符map

Observable.class

@CheckReturnValue
@SchedulerSupport(SchedulerSupport.NONE)
public final <R> Observable<R> map(Function<? super T, ? extends R> mapper) {
	//判空
    ObjectHelper.requireNonNull(mapper, "mapper is null");
    return RxJavaPlugins.onAssembly(new ObservableMap<T, R>(this, mapper));
}

RxJavaPlugins.onAssembly()前面已經分析過了是hook函數,默認不實現,可忽略,
所以此處返回 new ObservableMap<T, R>(this, mapper)

ObservableMap類

public final class ObservableMap<T, U> extends AbstractObservableWithUpstream<T, U> {...}

ObservableMap繼承AbstractObservableWithUpstream所以先看下類AbstractObservableWithUpstream

AbstractObservableWithUpstream類

abstract class AbstractObservableWithUpstream<T, U> extends Observable<U>
 implements HasUpstreamObservableSource<T> {

/** The source consumable Observable. */
protected final ObservableSource<T> source;

/**
 * Constructs the ObservableSource with the given consumable.
 * @param source the consumable Observable
 */
AbstractObservableWithUpstream(ObservableSource<T> source) {
	//構造函數 保存給定的ObservableSource
    this.source = source;
}

@Override
public final ObservableSource<T> source() {
    return source;
}
}

AbstractObservableWithUpstream代碼很簡單就是構造函數保存了給定的ObservableSource對象,
但是需要注意的是該類繼承Observable,所以ObservableMap也是一個Observable實例
接着獲取看ObservableMap類

ObservableMap類

public final class ObservableMap<T, U> extends AbstractObservableWithUpstream<T, U> {
final Function<? super T, ? extends U> function;

public ObservableMap(ObservableSource<T> source, Function<? super T, ? extends U> function) {
	//1
    super(source);
    this.function = function;
}

@Override
public void subscribeActual(Observer<? super U> t) {
	//2
    source.subscribe(new MapObserver<T, U>(t, function));
}
...
}

上述1處,調用父類的構造函數,存儲ObservableSource,而前面我們看到 map方法的實現是
Observable{
...
 public final <R> Observable<R> map(Function<? super T, ? extends R> mapper){
	return new ObservableMap<T, R>(this, mapper);
}
...
}

所以ObservableMap會存儲調用map方法的Observable實例,

上述2處 我們知道ObservableMap是一個Observable實例,
所以實現Observable的抽象方法subscribeActual(詳細的我們在第一篇中已經說過了)
subscribeActual方法中,使用存儲的Observable實例進行訂閱包裝後的Observer
我們接着先看下MapObserver類,在回頭總結

MapObserver類

//BasicFuseableObserver繼承與Observer
 static final class MapObserver<T, U> extends BasicFuseableObserver<T, U> {
    final Function<? super T, ? extends U> mapper;

    MapObserver(Observer<? super U> actual, Function<? super T, ? extends U> mapper) {
		//將 actual存儲爲downstream(父類的構造函數)
        super(actual);
		//存儲轉換的函數
        this.mapper = mapper;
    }

    @Override
    public void onNext(T t) {
		//在onError 和onComplete方法中會設置 done = true
        if (done) {
            return;
        }
		//上述分析的代碼中 sourceMode請求到的都是NONE
        if (sourceMode != NONE) {
            downstream.onNext(null);
            return;
        }

        U v;

        try {
			//調用存儲的Function方法對傳進來的參數t進行轉換爲v
            v = ObjectHelper.requireNonNull(mapper.apply(t), "The mapper function returned a null value.");
        } catch (Throwable ex) {
            fail(ex);
            return;
        }
		//調用下游的onNext(v)
        downstream.onNext(v);
    }
	//先行忽略 分析的代碼中requestFusion請求得到都是NONE
    @Override
    public int requestFusion(int mode) {
        return transitiveBoundaryFusion(mode);
    }
	//先行忽略 上述分析的代碼不會調用
    @Nullable
    @Override
    public U poll() throws Exception {
        T t = qd.poll();
        return t != null ? ObjectHelper.<U>requireNonNull(mapper.apply(t), "The mapper function returned a null value.") : null;
    }
}

我們現在先主要關注 事件流的 調用 先行忽略未用到的關於QueueFuseable方面的內容,後面的文章會詳細的說明

.

現在我們得到了關於map操作符的大致流程

  1. 生成一個ObservableMap並存儲調用map的Observable上流數據源
  2. subscribe(Observer)訂閱
  3. 包裝Observer生成new MapObserver<T, U>(Observer, function),當調用onNext(T t)應用給定的轉換函數
  4. 使用存儲的Observable調用subscribe(Observer)方法,即是source.subscribe(new MapObserver<T, U>(t, function));

現在map的大概流程分析,接下來模擬最上面代碼整個事件的流程

整個代碼流程:
new ObservableMap<T, R>(new ObservableMap<T, R>(new ObservableCreate<T>(new ObservableOnSubscribe(){}), Function mapper), Function mapper).subscribe(new Observer(){})
回調訂閱流程如下:
ObservableCreate.subscribe(new MapObserver<T, U>((new MapObserver<T, U>(new new Observer(){}, function),function));

一步步拆分

生成Observable過程,最終生成Observable C
Observable A = new ObservableCreate<T>(new ObservableOnSubscribe(){})
Observable B = new ObservableMap<T, R>(A, Function mapper)
Observable C = new ObservableMap<T, R>(B, Function mapper)

訂閱過程
Observer D = new Observer(){}
C.subscribe(D)

拆分C.subscribe(D),最終生成一個經過兩個包裝的Observer,然後源發射源進行訂閱該Observer
C.subscribe(D)
	->內部調用
	Observer E =new MapObserver<T, U>(D, function)
	B.subscribe(E)
		->內部調用
		A.subscribe(new MapObserver<T, U>(E, function))

整個流程示意圖如下:

事件流示意圖

通過上面的分析可以得到,每個操作符既是一個觀察者,訂閱上面的數據流,也是一個被觀察者,發送經過其處理的數據源,
所以:RxJava形成的可觀察事件序列,除了首尾,中間事件節點,都是既是觀察者又是被觀察者,其向上訂閱,向下分發數據,
我們可以將RxJava形成的事件序列可稱爲數據流,數據從最初的Observable流向最後的Observer,
所以可以稱最初的Observable爲上游,最後的Observer爲下游

總結:

  1. RxJava形成的可觀察事件序列是一個數據流,最初的Observable爲上游,最後的Observer爲下游
  2. 數據從上游流向下流,訂閱從下游向上遊訂閱
  3. 數據流中間節點,每一個節點既是觀察者也是被觀察者
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章