JianDanRxJava icon indicating copy to clipboard operation
JianDanRxJava copied to clipboard

[改进]缓存时的处理

Open kyleada opened this issue 9 years ago • 6 comments

https://github.com/ZhaoKaiQiang/JianDanRxJava/blob/master/app/src/main/java/com/socks/jiandan/adapter/VideoAdapter.java#L182

这里的处理是在doOnNext里保存到数据库缓存,在subscribe里更新数据到界面上。我测试了下,虽然doOnNext设置了新线程运行,长时间也不会阻塞主线程,但根据我的测试,直到doOnNext里函数执行完毕,才会执行subscriber里的onNext, 但实际场景里我们不希望更新Ui的操作是在保存到数据库执行完毕后在进行吧?假设这个操作执行了很长时间,而且并不关心保存到数据库成功与否。

是不是有更好的处理办法?

kyleada avatar Jan 21 '16 01:01 kyleada

这确实是一个问题,我之前想在onComplate()里面处理,即onNext()中显示结果之后再保存数据库,但是这样做的话,不能指定onComplate()的线程,只能和onNext()在同一个线程,但是这样做又会可能阻塞UI,所以暂时也没有好办法,我请教过朱凯,他也没有更好的解决方案,如果你知道更好的做法的话,可以继续交流^_^

ZhaoKaiQiang avatar Jan 21 '16 01:01 ZhaoKaiQiang

我又想了下,这样做好像没有什么问题,因为在doOnNext()中会另外开启线程来处理,并不会缓存保存完才显示,而是开启线程之后,onNext()就执行了,你可以在doOnNext()中Sleep一下,就可以看出结果了,这样做应该是没问题的

ZhaoKaiQiang avatar Jan 21 '16 01:01 ZhaoKaiQiang

           .observeOn(Schedulers.newThread())
                    .doOnNext(new Action1<String>() {
                @Override
                public void call(String s) {
                    try {
                        Thread.sleep(20000);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                    s = "00000";
                    Log.e("doOnNext",Thread.currentThread().getName());
                }
            }).observeOn(AndroidSchedulers.mainThread())
                    .subscribe(new Action1<String>() {
                @Override
                public void call(String s) {
                    Log.e("subscribe",Thread.currentThread().getName());

                }
            });

我就是这么测的,但结果是20s后 Log.e("subscribe",Thread.currentThread().getName());才输出

kyleada avatar Jan 21 '16 01:01 kyleada

observeOn(Schedulers.newThread()) 应该是 subscribeOn

ZhaoKaiQiang avatar Jan 21 '16 02:01 ZhaoKaiQiang

今天看了这篇文章找到解决方法了

public static void storeBitmap(Context context, Bitmap bitmap, String filename) { Schedulers.io().createWorker().schedule(() -> { blockingStoreBitmap(context, bitmap, filename); }); }

我记在了我的博客

kyleada avatar Mar 01 '16 07:03 kyleada

再请教个问题啊,其实我最喜欢RxJava的就是切换线程方便。AsyncTask有个大的缺陷是不能很好的cancel掉任务,RxJava除了最后取消订阅,怎么去取消里面封装的任务啊?如果是用RxJava + okHttp请求的话,怎么合理的封装okHttp的cancel暴露出来?谢谢

kyleada avatar Mar 01 '16 07:03 kyleada