只能用 flatmap 而不能用 map 的场景

遇到一个问题,问:请举个只能使用flatmap而不能使用map的例子?笔者当时思考了一下,头脑发热,没有思考完整呀!!!

区别

  • map返回的是结果集,flatmap返回的是包含结果集的Observable。
  • map只能进行一对一的对象转换,而不能将对象转换成对象数组。
  • map一般用于一对一,而flatmap一般用于一对多或者多对多。
  • flatMap() 中返回的是个 Observable 对象,并且这个 Observable 对象并不是被直接发送到了 Subscriber的回调方法中,而是立即激活并执行。

举例

答:当我们输入一个urls列表,希望按顺序的一个一个的发起网络请求,只要有一个请请中断,则后续请求全部中断,这个时候只能使用flatmap。原因是flatmap是返回 Observable 的,我们可以利用 Observable 对结果集进行转换,将单一结果集对象转换成数组结果集对象,而map是做不到这一点的。

map调用:

 Observable.just(urlList)
                .map(new Func1<List<String>, String>() {
                    @Override
                    public String call(List<String> urls) {
                        return urls.get(0);
                    }
                })
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(new Action1<String>() {
                    @Override
                    public void call(String url) {
                        Log.d(TAG, "url = " + url);
                    }
                }, new Action1<Throwable>() {
                    @Override
                    public void call(Throwable throwable) {

                    }
                });

输出结果:

02-27 23:13:48.335 1565-1565/? D/MainActivity: url = http://www.baidu.com

通过输入我们可以看到,map的每次返回只是返回了一个单一的结果。

flatmap调用:

Observable.just(urlList)
                .flatMap(new Func1<List<String>, Observable<String>>() {
                    @Override
                    public Observable<String> call(List<String> urls) {
                        return Observable.from(urls);
                    }
                })
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(new Action1<String>() {
                    @Override
                    public void call(String s) {
                        Log.d(TAG, "url = " + s);
                    }
                }, new Action1<Throwable>() {
                    @Override
                    public void call(Throwable throwable) {

                    }
                });

输出结果:

02-27 23:17:13.265 6527-6527/com.meizu.rxjava.example D/MainActivity: url = http://www.baidu.com
02-27 23:17:13.265 6527-6527/com.meizu.rxjava.example D/MainActivity: url = http://ngudream.com

通过输入结果,我们可以看到 flatmap 通过 Observable.from(urls) 的转换,可以将结果分散成单一的 item,顺序返回。

对以上回答并不满意吧,嗯嗯,是的!

那再来考虑另一个场景:在一个请求中,我们希望输入数据后,通过异步处理再将处理后的结果分发到下一步,这个时候使用 map 就无法满足条件,因为 map 是一个同步闭包方法,是需要直接返回结果的,但是 flatmap 就不一样,我们可以通过 Observable 来进行转化,将新的 Observable 转化在别的线程中激活执行。

先写到这,容我再想想…

文章目录
  1. 1. 区别
  2. 2. 举例
|