create

Observable分为cold以及hot两种,cold主要是静态的,每次subscribe都是从头开始互不干扰,而hot的在同一时刻获得的值是一致的

cold Observable

使用create创建的Observable都是属于cold的Observable

@Test
public void coldObs() throws InterruptedException {
    Observable obs=Observable.create(sub->{
		//在新线程上emit对象
        new Thread(()->{
        int i=0;
        while(i<5){
            sub.onNext(i++);
            try {
                Thread.sleep(500);
            } catch (InterruptedException e) {
            }
        }}).start();
    });
    obs.subscribe(x->System.out.println("1st sub "+x));
    Thread.sleep(1000);
    obs.subscribe(x->System.out.println("2nd sub "+x));
    while(true){
        Thread.sleep(10000);
    }
}
-----输出-----
1st sub 0
1st sub 1
2nd sub 0
1st sub 2
2nd sub 1
1st sub 3
2nd sub 2
1st sub 4
2nd sub 3
2nd sub 4

可以看到两个subscribe相隔1s订阅,两个值互不相关。

hot Observable

coldObs可以转换为hotObservable,hot主要是使用在比如鼠标操作等事件上的

@Test
public void hotObs() throws InterruptedException {
    ConnectableObservable obs=Observable.create(sub->{
		//在新线程上emit对象
        new Thread(()->{
            int i=0;
            while(i<5){
                sub.onNext(i++);
                try {
                    Thread.sleep(500);
                } catch (InterruptedException e) {
                }
            }}).start();
    }).publish();
	//开始emit对象
    obs.connect();
    obs.subscribe(x->System.out.println("1st sub "+x));
    Thread.sleep(1000);
    obs.subscribe(x->System.out.println("2nd sub "+x));
    while(true){
        Thread.sleep(10000);
    }
}
-----输出-----
1st sub 1
1st sub 2
1st sub 3
2nd sub 3
1st sub 4
2nd sub 4

使用publish和connect之后就开始向subscriber发送对象,无论当前有几个subscriber,同一时刻subscriber得到的值也是一样的

源码分析

RxJava中有内置的钩子函数可以将函数注册在RxJavaHooks的各个方法上来改变各个环节的操作,包括Observable创建,运行时等
Observable的create方法只是注册了对应emit的OnSubscribe对象

    public static <T> Observable<T> create(OnSubscribe<T> f) {
		//调用protected构造方法,这里使用RxJavaHooks的onCreate方法
        return new Observable<T>(RxJavaHooks.onCreate(f));
    }
	protected Observable(OnSubscribe<T> f) {
        this.onSubscribe = f;
    }

正真运行Observable的是subscriber订阅时触发的

public final Subscription subscribe(Subscriber<? super T> subscriber) {
    return Observable.subscribe(subscriber, this);
}

static <T> Subscription subscribe(Subscriber<? super T> subscriber, Observable<T> observable) {
    if (subscriber == null) {
        throw new IllegalArgumentException("subscriber can not be null");
    }
    if (observable.onSubscribe == null) {
        throw new IllegalStateException("onSubscribe function can not be null.");
    }

	//调用subscriber的onStart方法
    subscriber.onStart();

    //使用SafeSubscriber包装原有的Subscriber,SafeSubscriber装饰原来的Subscriber保证当调用onComplete或onError后不会再调用任何方法。
    if (!(subscriber instanceof SafeSubscriber)) {
        subscriber = new SafeSubscriber<T>(subscriber);
    }

    try {
		//使用JavaHooks的onObservableStart拦截的onSubscribe,并调用subscriber
        RxJavaHooks.onObservableStart(observable, observable.onSubscribe).call(subscriber);
		//当结束调用RxJavaHooks的onObservableReturn拦截方法
        return RxJavaHooks.onObservableReturn(subscriber);
    } catch (Throwable e) {
		...
    }
}

这个是cold Observable的流程,下面看下Observable的publish和connect的逻辑

//Observable.java
//publish方法包装原来的Observable返回ConnectableObservable
public final ConnectableObservable<T> publish() {
    return OperatorPublish.create(this);
}

//OperatorPublish.java
public static <T> ConnectableObservable<T> create(Observable<? extends T> source) {
	//订阅在原始Observable上的Subscriber
    final AtomicReference<PublishSubscriber<T>> curr = new AtomicReference<PublishSubscriber<T>>();
	//ConnectableObservable的OnSubscribe,提供外界Subscriber订阅
    OnSubscribe<T> onSubscribe = new OnSubscribe<T>() {
        @Override
        public void call(Subscriber<? super T> child) {
            for (;;) {
                PublishSubscriber<T> r = curr.get();
                if (r == null || r.isUnsubscribed()) {
					//这个Subscriber是用于订阅到原始Observable上的,这里只是初始化,并没有开始订阅
                    PublishSubscriber<T> u = new PublishSubscriber<T>(curr);
                    u.init();
                    if (!curr.compareAndSet(r, u)) {
                        continue;
                    }
                    r = u;
                }

                InnerProducer<T> inner = new InnerProducer<T>(r, child);
				 //将订阅的子subscriber添加到PublishSubscriber上
                if (r.add(inner)) {
                    child.add(inner);
                    child.setProducer(inner);
                    break; // NOPMD
                }
            }
        }
    };
    return new OperatorPublish<T>(onSubscribe, source, curr);
}

//connect方法将PublishSubscriber订阅到原始的Observable,
//ConnectableObservble.java
public final Subscription connect() {
    final Subscription[] out = new Subscription[1];
	//调用OperatorPublish的connect方法
    connect(new Action1<Subscription>() {
        @Override
        public void call(Subscription t1) {
            out[0] = t1;
        }
    });
    return out[0];
}

//OperatorPublish.java
public void connect(Action1<? super Subscription> connection) {
    boolean doConnect;
    PublishSubscriber<T> ps;
	//防止竞态条件使用CAS来初始化PublishSubscriber
    for (;;) {
        ps = current.get();
        if (ps == null || ps.isUnsubscribed()) {
            PublishSubscriber<T> u = new PublishSubscriber<T>(current);
            u.init();
            if (!current.compareAndSet(ps, u)) {
                continue;
            }
            ps = u;
        }
        doConnect = !ps.shouldConnect.get() && ps.shouldConnect.compareAndSet(false, true);
        break; // NOPMD
    }
    connection.call(ps);
    if (doConnect) {
		//如果之前没有订阅过,那么就订阅到原始的Observable上
        source.unsafeSubscribe(ps);
    }
}

//PublishSubscriber.java
//这个是订阅到原始Observable上的Subscriber,当触发onNext时的逻辑
public void onNext(T t) {
	//将原始Observable发出的对象放入一个队列
    if (!queue.offer(NotificationLite.next(t))) {
        onError(new MissingBackpressureException());
    } else {
		//调用dispatch方法可以将队列的内容发送个订阅的子Subscriber
        dispatch();
    }
}

//将值分发到各个子Subscriber上
void dispatch() {
	...
	//从队列中取得值
    Object v = queue.poll();
	...
	//处理null
	T value = NotificationLite.getValue(v);
	...
	//循环所有的InnerProducer(之前的在onSubscribe中add在Subsciber上的)
	for (InnerProducer<T> ip : ps) {
		if (ip.get() > 0L) {
			try {
				//把value传递给child的onNext
				ip.child.onNext(value);
			} catch (Throwable t) {
				ip.unsubscribe();
				Exceptions.throwOrReport(t, ip.child, value);
				continue;
			}
			ip.produced(1);
		}
	}
	...
}

hot的Observable就是自己监听原始的Observable然后广播给注册在上的子Subscriber,从而达到能够让所有子Subscriber取得一样的数据。