Rxjava为了保持链式调用和简单便捷性,设计了各种方便的操作符,刚刚接触Rxjava的我都能深深的感觉到这一点。从源码来说操作符就是对Publisher内的OnObserver对象的层层代理,我称之为“链式”代理,不知道合不合适,就像链表,或者说像套娃,一个代理套着一个代理。
1.变换的抽象接口:Rxjava中操作符逻辑实体继承于Func1接口,即单参数带返回值的call回调接口。这里也是一样
public interface Func1<I,O> {
public O call(I i);
}
这里直接给到了Func1接口,此接口交由用户实现。
2.变换的代理即各类操作符的具体实现,这里我选择使用抽象类,而RxJava则是接口Operator,区别在于,抽象类可以封装更多的东西,实现类的压力较小。
public abstract class Change<I,O> implements OnObserver<I>,IObserverProxy<O> {
protected OnObserver<O> preChange;
protected Func1 changeImpl;
protected IObserverProxy iObserverProxy;
public Change(OnObserver<I> preChange) {
this.preChange = (OnObserver<O>) preChange;
iObserverProxy = (IObserverProxy<I>) preChange;
}
public Change() {
}
@Override
public void addObserver(OnObserver observer) {
iObserverProxy.addObserver(observer);
}
@Override
public void rmObserver(OnObserver observer) {
iObserverProxy.addObserver(observer);
}
@Override
public void clear() {
iObserverProxy.clear();
}
@Override
public Vector<OnObserver<O>> getObservers() {
return iObserverProxy.getObservers();
}
@Override
public void onError(Throwable throwable) {
preChange.onError(throwable);
}
@Override
public void onFinished() {
preChange.onFinished();
}
public void setPreChange(OnObserver<I> preChange){
this.preChange = (OnObserver<O>) preChange;
iObserverProxy = (IObserverProxy<I>) preChange;
}
public void setChangeImpl(Func1 changeImpl) {
this.changeImpl = changeImpl;
}
}
这里要注意的是上一篇所说的RxJava事件消费时机与本作有很大不同,RxJava调用一个操作符便直接执行了,而本作类似传统的观察者模式,选择了post触发之后统一执行。所以这里的实现还是有很大不同的
3.几个常用的变换:
1).Map转换参数类型,即在发布-订阅途中转换数据流类型
public class MapChange<I,O> extends Change<I,O>{
@Override
public void onSuccess(I i) {
preChange.onSuccess((O) changeImpl.call(i));
}
}
很简单 changeImpl就是用户实现的Func1接口
我们来对比一下RxJava的OperatorMap
public final class OperatorMap<T, R> implements Operator<R, T> {
final Func1<? super T, ? extends R> transformer;
public OperatorMap(Func1<? super T, ? extends R> transformer) {
this.transformer = transformer;
}
@Override
public Subscriber<? super T> call(final Subscriber<? super R> o) {
return new Subscriber<T>(o) {
@Override
public void onCompleted() {
o.onCompleted();
}
@Override
public void onError(Throwable e) {
o.onError(e);
}
@Override
public void onNext(T t) {
try {
o.onNext(transformer.call(t));
} catch (Throwable e) {
Exceptions.throwOrReport(e, this, t);
}
}
};
可以发现还是有很大不同的,原因就是消费时机的不同导致的设计不同。
2).FilterChange 在数据流中过滤无用数据
public class FilterChange<T> extends Change<T,T>{
@Override
public void onSuccess(T t) {
if ((Boolean) changeImpl.call(t))
preChange.onSuccess(t);
}
}
3).还有个集合展开 with(T[] ts)和上面几个不同,这是对OnPublisher的代理
public IPublisher<T> create(final T[] ts) {
onPublisher = new OnPublisher<T>() {
@Override
public void call(OnObserver<T> observer) {
for (T t:ts)
observer.onSuccess(t);
observer.onFinished();
}
};
return this;
}
隐式创建一个OnOperator
等等,除此之外还有很多,但是实现原理都是大同小异。
4.关于“链式”代理的顺序问题,还是上面调用时机的问题,
private Change changeHead;
private Change changeLast;
需要保存头尾的change对象,后来的change被前面的change代理这样才能保证调用时的顺序。
5.Publisher中change方法
public <I, O> IPublisher<T> change(Func1<I, O> change,Change changeProxy) {
changeProxy.setChangeImpl(change);
changeLast.setPreChange(changeProxy);
changeLast = changeProxy;
return this;
}
例如filter操作
public IPublisher<T> filted(OnFilter<T> filter) {
Change<T,T> filterChange = new FilterChange<T>();
change(filter,filterChange);
return this;
}
map操作
public <I, O> IPublisher<T> maped(Func1<I, O> maped) {
Change<I,O> mapChange = new MapChange<I,O>();
change(maped,mapChange);
return this;
}
第三篇的最后,暂时还有最后一期,讲这个小Rx框架扩展成EventBus,相信大家会有兴趣