subscribeOn() 源码分析
给上面的代码分配线程
Observable.create(new ObservableOnSubscribe<String>() {
@Override
public void subscribe(ObservableEmitter<String> e) throws Exception {
e.onNext("AAA");
}
})
//ObservableCreate.subscribeOn
.subscribeOn(Schedulers.io())
//SubscribeOnObserver.subscribe
.subscribe(new Observer<String>() {
@Override
public void onSubscribe(Disposable d) {
}
@Override
public void onNext(String s) {
}
@Override
public void onError(Throwable e) {
}
@Override
public void onComplete() {
}
});
点进Schedulers.io() 看看到底做了什么?
IO = RxJavaPlugins.initIoScheduler(new IOTask());
初始化的时候传入了 new IOTask() 继续往里面跟,其实这里面就是一个线程池。
就是这样一种流程,我们再来看.subscribe 其实也就相当于是SubscribeOnObserver.subscribe,点进去看看 其实这个流程和前面分析的流程都是一样的 最终会走到
@Override
public void subscribeActual(final Observer<? super T> s) {
final SubscribeOnObserver<T> parent = new SubscribeOnObserver<T>(s);
s.onSubscribe(parent);
parent.setDisposable(scheduler.scheduleDirect(new SubscribeTask(parent)));
}
又是一个包裹 然后传给new SubscribeTask()
final class SubscribeTask implements Runnable {
private final SubscribeOnObserver<T> parent;
SubscribeTask(SubscribeOnObserver<T> parent) {
this.parent = parent;
}
@Override
public void run() {
source.subscribe(parent);
}
}
毋庸置疑SubscribeTask这段代码肯定会抛给线程池来执行的
我们来看下整体的流程
可以看到线程池执行完任务之后都是异步 到终点也是异步 显然是不行的。所以需要切换到主线程。
ObserveOn() 源码分析
给下面的代码分配线程
Observable.create(new ObservableOnSubscribe<String>() {
@Override
public void subscribe(ObservableEmitter<String> e) throws Exception {
e.onNext("AAA");
}
})
//ObservableCreate.subscribeOn
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
//observeOnObserver.subscribe
.subscribe(new Observer<String>() {
@Override
public void onSubscribe(Disposable d) {
}
@Override
public void onNext(String s) {
}
@Override
public void onError(Throwable e) {
}
@Override
public void onComplete() {
}
});
加上 .observeOn(AndroidSchedulers.mainThread()) 就可以切换主线程了,我们看下怎么做的
还是一样的流程 看源码,先看AndroidSchedulers.mainThread() 最终返回的是Scheduler MAIN_THREAD,
大概流程 是这样的 Scheduler MAIN_THREAD ----> DEFAULT = new HandlerScheduler(new Handler(Looper.getMainLooper()))--->HandlerScheduler$HandlerWorker schedule{ handler.sendMessageDelayed(run) } 这段伪代码就是大概的流程了
自定义操作符
明白了整个思想和流程之后 ,依葫芦画瓢自定义操作符就很简单了,我们来自定义一个防抖的操作符
首先 定以一个 RxView类 里面有一个静态方法(操作符)
public class RxView {
public static Observable<Object> clicks(View view) {
return new ViewClickObservable(view);
}
}
public class ViewClickObservable extends Observable<Object> {
private final View view;
private static final Object EVENT = new Object();
public ViewClickObservable(View view) {
this.view = view;
}
@Override
protected void subscribeActual(Observer<? super Object> observer) {
// 可以干自己的事情
MyListener myListener = new MyListener(view, observer);
observer.onSubscribe(myListener);
this.view.setOnClickListener(myListener);
}
// 包裹
static final class MyListener implements View.OnClickListener, Disposable {
private final View view;
private Observer<Object> observer;
private final AtomicBoolean isDisposable = new AtomicBoolean();
public MyListener(View view, Observer<Object> observer) {
this.view = view;
this.observer = observer;
}
@Override
public void onClick(View v) {
if (isDisposed() == false) {
observer.onNext(EVENT);
}
}
@Override
public void dispose() {
if (isDisposable.compareAndSet(false, true)) {
if (Looper.myLooper() == Looper.getMainLooper()) {
view.setOnClickListener(null);
} else {
AndroidSchedulers.mainThread().scheduleDirect(new Runnable() {
@Override
public void run() {
view.setOnClickListener(null);
}
});
}
}
}
@Override
public boolean isDisposed() {
return isDisposable.get();
}
}
}
现在就可以正常使用了 其实就是仿写了