RxJava操作符源码传送门
- https://github.com/xiehui999/fuseProgram
在上篇文章RxJava操作符系列一我们介绍的操作符几乎都是创建被观察者的操作符,那么今天的这篇文章就介绍一下经常用到的转换操作符。话不多说,开始上车。
Map
该操作符是对原始Observable发射的每一项数据运用一个函数,然后返回一个发射这些结果的Observable。
例如我们有一个整形数组的数据,当大于5时输出为true,则代码实现
- Integer[] integers = {0, 9, 6, 4, 8};
- Observable.from(integers).map(new Func1() {
- @Override
- public Boolean call(Integer integer) {
- Log.e(TAG, "call: "+integer);
- return (integer > 5);
- }
- }).subscribe(new Subscriber() {
- @Override
- public void onCompleted() {
- Log.e(TAG, "onCompleted: ");
- }
- @Override
- public void onError(Throwable e) {
- Log.e(TAG, "onError: ");
- }
- @Override
- public void onNext(Boolean aBoolean) {
- Log.e(TAG, "onNext: "+aBoolean);
- }
- });
日志输出信息
- call: 0
- onNext: false
- call: 9
- onNext: true
- call: 6
- onNext: true
- call: 4
- onNext: false
- call: 8
- onNext: true
- onCompleted:
对于map,他可以将将数据源变换为你想要的类型,比如,你想获取有一个Student对象(里面age,name属性)那么我们可以通过map只获取name。接下来。我们再举个例子,我们根据一个图片路径获取图片并将图片设置到ImageView,然后将ImageView加的我们的布局中。
- String path = Environment.getExternalStorageDirectory()+ File.separator+"aaa.jpg";
- Observable.just(path)
- .subscribeOn(Schedulers.io())
- .map(new Func1() {
- @Override
- public Bitmap call(String s) {
- Bitmap bitmap = BitmapFactory.decodeFile(s);
- Log.e(TAG, "call: Bitmap"+bitmap);
- return bitmap;
- }
- }).map(new Func1() {
- @Override
- public ImageView call(Bitmap bitmap) {
- Log.e(TAG, "call: ImageView");
- ImageView imageView = new ImageView(getActivity());
- LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.WRAP_CONTENT, LinearLayout.LayoutParams.WRAP_CONTENT);
- imageView.setLayoutParams(params);
- imageView.setImageBitmap(bitmap);
- return imageView;
- }
- }).observeOn(AndroidSchedulers.mainThread())
- .subscribe(new Subscriber() {
- @Override
- public void onCompleted() {
- Log.e(TAG, "onCompleted: ");
- }
- @Override
- public void onError(Throwable e) {
- Log.e(TAG, "onError: ");
- }
- @Override
- public void onNext(ImageView imageView) {
- Log.e(TAG, "onNext: ");
- layout.addView(imageView);
- }
- });
Cast
该操作符就是做一些强制类型转换操作的。例如,当我们在页面跳转时数据对象往往是序列化的,当我们在新的页面收到数据后就要强制转换为我们想要的类型。cast操作符也可以实现这样的功能。如下
- Observable.just(serializable).cast(FileInfo.class).subscribe(new Subscriber() {
- @Override
- public void onCompleted() {
- Log.e(TAG, "onCompleted: " );
- }
- @Override
- public void onError(Throwable e) {
- Log.e(TAG, "onError: " );
- }
- @Override
- public void onNext(FileInfo fileInfo) {
- Log.e(TAG, "onNext: "+fileInfo.toString());
- tv1.append("\n"+fileInfo.toString());
- }
- });
不过在该操作符实际用途并没有那么的广泛,很少用到,当然这个操作符也可以达到java 中instanceof相同的作用,用于类型检查,当不是该类型就会执行onError()方法。
FlatMap
该操作符与map操作符的区别是它将一个发射数据的Observable变换为多个Observables,然后将它们发射的数据合并后放进一个单独的Observable.
- Integer[] integers = {1, 2, 3};
- Observable.from(integers).flatMap(new Func1>() {
- @Override
- public Observable call(final Integer integer) {
- return Observable.create(new Observable.OnSubscribe() {
- @Override
- public void call(Subscriber super String> subscriber) {
- Log.e(TAG, "call: FlatMap " + Thread.currentThread().getName());
- try {
- Thread.sleep(200);
- subscriber.onNext(integer + 100 + " FlatMap");
- subscriber.onCompleted();
- } catch (InterruptedException e) {
- e.printStackTrace();
- subscriber.onError(e);
- }
- }
- }).subscribeOn(Schedulers.newThread());
- }
- }).observeOn(AndroidSchedulers.mainThread())
- .subscribe(new Subscriber() {
- @Override
- public void onCompleted() {
- Log.e(TAG, "onCompleted: FlatMap");
- }
- @Override
- public void onError(Throwable e) {
- Log.e(TAG, "onError: FlatMap");
- }
- @Override
- public void onNext(String s) {
- Log.e(TAG, "onNext: FlatMap " + s);
- }
- });
打印日志信息
- call: FlatMap RxNewThreadScheduler-2
- call: FlatMap RxNewThreadScheduler-3
- call: FlatMap RxNewThreadScheduler-4
- onNext: FlatMap 101 FlatMap
- onNext: FlatMap 102 FlatMap
- onNext: FlatMap 103 FlatMap
- onCompleted: FlatMap
ConcatMap
该操作符是类似于最简单版本的flatMap,但是它按次序连接而不是合并那些生成的Observables,然后产生自己的数据序列.将上述flatMap代码更改如下
- Integer[] integers = {1, 2, 3};
- Observable.from(integers).concatMap(new Func1>() {
- @Override
- public Observable call(final Integer integer) {
- return Observable.create(new Observable.OnSubscribe() {
- @Override
- public void call(Subscriber super String> subscriber) {
- Log.e(TAG, "call:2 ConcatMap " + Thread.currentThread().getName());
- try {
- Thread.sleep(200);
- subscriber.onNext(integer + 100 + " ConcatMap");
- subscriber.onCompleted();
- } catch (InterruptedException e) {
- e.printStackTrace();
- subscriber.onError(e);
- }
- }
- }).subscribeOn(Schedulers.newThread());
- }
- }).observeOn(AndroidSchedulers.mainThread())
- .subscribe(new Subscriber() {
- @Override
- public void onCompleted() {
- Log.e(TAG, "onCompleted: ConcatMap");
- }
- @Override
- public void onError(Throwable e) {
- Log.e(TAG, "onError: ConcatMap");
- }
- @Override
- public void onNext(String s) {
- Log.e(TAG, "onNext: ConcatMap " +s);
- }
- });
接下文