This article transferred from: HTTP://BLOG.CSDN.NET/ADZCSX2
Rxjava is now a very avant-garde asynchronous framework, but also because he is very new, so it is more difficult to navigate.
Just like Okhttp calls its Cancel method directly in OnStop or OnDestroy, but Rxjava is not that simple.
Because if each request get observable object, and then OnStop in unsubscribe Cancel, this is not conducive to encapsulation. And it will cause a lot of code, so I found a solution with rxlifecycle.
Pilot Pack
‘com.trello:rxlifecycle:0.5.0‘ ‘com.trello:rxlifecycle-components:0.5.0‘
Then write rxactivity, the original author GitHub on the source code, I based on my own situation slightly modified a bit.
ImportAndroid.os.Bundle;ImportAndroid.support.annotation.CallSuper;ImportAndroid.support.annotation.NonNull;Importandroid.support.v4.app.FragmentActivity;ImportCom.trello.rxlifecycle.ActivityEvent;ImportCom.trello.rxlifecycle.ActivityLifecycleProvider;ImportCom.trello.rxlifecycle.RxLifecycle;ImportRx. Observable;ImportRx.subjects.BehaviorSubject;/** * Created by a on 2016/5/6. * * Public class rxactivity extends fragmentactivity implements Activitylifecycleprovider { Public Finalbehaviorsubject<activityevent> lifecyclesubject = Behaviorsubject.create ();@NonNull @Override PublicObservable<activityevent>Lifecycle() {returnLifecyclesubject.asobservable (); }@NonNull @Override Public<T> Observable.transformer<t, t>binduntilevent(@NonNull activityevent event) {returnRxlifecycle.binduntilevent (Lifecyclesubject, event); }@NonNull @Override Public<T> Observable.transformer<t, t>bindtolifecycle() {returnRxlifecycle.bindactivity (Lifecyclesubject); }@Override @CallSuper protected void onCreate(Bundle savedinstancestate) {Super. OnCreate (Savedinstancestate); Lifecyclesubject.onnext (activityevent.create); }@Override @CallSuper protected void OnStart() {Super. OnStart (); Lifecyclesubject.onnext (Activityevent.start); }@Override @CallSuper protected void Onresume() {Super. Onresume (); Lifecyclesubject.onnext (Activityevent.resume); }@Override @CallSuper protected void OnPause() {lifecyclesubject.onnext (activityevent.pause);Super. OnPause (); }@Override @CallSuper protected void OnStop() {lifecyclesubject.onnext (activityevent.stop);Super. OnStop (); }@Override @CallSuper protected void OnDestroy() {lifecyclesubject.onnext (Activityevent.destroy);Super. OnDestroy (); }}
Inherit the rxactivity with your own activity. Add a place to the network request
. Compose (Rxlifecycle.binduntilevent (Lifecycle (), activityevent.stop))
This means canceling the request at the stop cycle.
I used the previous blog upload Image example, now is mainactivity into secondactivity, click the button after uploading a picture, and then get the results returned.
File File =NewFile (environment.getexternalstoragedirectory () +"/123.png"); Httputil.getiimagepp (). Uploadimage ("C1a2b3ab56a2f218aed9b2ab3c16ce88","be8318b73cef1c2bcafb6c8a77922436", Httputil.postfileparams ("img", file))//encapsulates the main thread subscribe running in a sub-thread, the following will tell how to encapsulate. . Compose (Rxhelper.io_main (secondactivity. This))//.compose (Rxlifecycle.binduntilevent (Lifecycle (), activityevent.stop)). Subscribe (NewRxsubscriber<object> () {@Override Public void _onnext(Object o) {L.E ("AAAA"); Tv.settext (String) o); }@Override Public void _OnError(String msg) { } });
Without adding. Compose (rxlifecycle.binduntilevent (Lifecycle (), activityevent.stop), click the button to upload and immediately return to the log log of the previous activity:
After returning to Mainactivity, about 2 seconds later, this sentence appears.
05-0618:37:58.59015642-15642/com.sanniuben.myapplication E/way: aaaa
After the addition, there was no return.
It can be seen that he canceled the request at the time of OnStop.
Rxlifecycle github:https://github.com/trello/rxlifecycle
Rxfragment Source page
Https://github.com/trello/RxLifecycle/tree/master/rxlifecycle-components/src/main/java/com/trello/rxlifecycle/components
The fragment operation is similar to this. Just need to inherit rxfragment
Next is the encapsulation.
Public classrxhelper<t> {//Sub-thread run, main thread callback //Note that this cannot be set to static, and the generics cannot be used after being set to static. That's why I subcribe the generics only for object reasons, and now blogs have been updated. PublicObservable.transformer<t, t>Io_main(Final rxactivity context) {return NewObservable.transformer<t, t> () {@Override PublicObservable<t>Pager(observable<t> tobservable) {observable<t> TObservable1 = (observable<t>) tobservable. Subscribeon ( Schedulers.io ()). Doonsubscribe (NewAction0 () {@Override Public void Pager() {A weak reference is implemented in the//progressdialogutil.showprogress and does not cause a memory leak. Progressdialogutil.showprogress (Context,"Loading, please wait"); }}). Subscribeon (Androidschedulers.mainthread ()). OB Serveon (Androidschedulers.mainthread ()). Compose (Rxlifecycle.binduntilevent (Context.lifecycle (), Ac Tivityevent.stop));returnTObservable1; } }; }}
Subscriber
/** * Created by a on 2016/5/6. * * Public Abstract classRxsubscriber<t> extends subscriber<t>{@Override Public void oncompleted() {//Cancel the dialog box when finishedProgressdialogutil.dismiss (); } @Override Public void OnError(Throwable e) {E.printstacktrace (); _OnError (E.getmessage ());if(! Netutils.isconnected (Myapplication.getcontextobject ())) {Toast.maketext (Myapplication.getcontextobject ()),"The request failed, please check the network!", Toast.length_short). Show (); Progressdialogutil.dismiss ();return; }} @Override Public void OnNext(T T) {_onnext (t); } Public Abstract void_OnNext(T T); Public Abstract void_OnError(String msg);}
Now take a look at the new request
File File =NewFile (environment.getexternalstoragedirectory () +"/123.png"); Httputil.getiimagepp (). Uploadimage ("C1a2b3ab56a2f218aed9b2ab3c16ce88","be8318b73cef1c2bcafb6c8a77922436", Httputil.postfileparams ("img", file))//Just add this sentence,rxhelper<t> generic content needs to be entered by itself. Compose (NewRxhelper<string>.io_main (secondactivity. This))//Here is new's our own Rxsubscriber. Subscribe (NewRxsubscriber<string> () {@Override Public void _onnext(String o) {L.E ("AAAA"); Tv.settext (o); }@Override Public void _OnError(String msg) { } });
This completes the encapsulation of the Rxjava. Now, every time you access the network, the dialog box is displayed, and the cancel dialog is requested, and the request is canceled at the activity lifecycle stop.
Transformer is actually a func1< observable< T, observable< r>> In other words: it is possible to convert one type of observable into another type of observable, and the invocation of a series of inline operators is identical.
The difference between compose and Flatmap ():
What is about FlatMap ()?
1. At the wondering, the difference is between using compose () and FlatMap (). They both emit Observable, which means both can reuse a series of operators, right?
The difference is this compose () is a higher level abstraction:it operates on the entire stream, not individually emitted Items. In more specific terms:
2, Compose () is the only-to-get-original Observable from the stream. Therefore, operators that affect the whole stream (like Subscribeon () and Observeon ()) need to use compose ().
In contrast, if you put Subscribeon ()/observeon () on FlatMap (), it would only affect the Observable you create in FlatMap ( ) but not the rest of the stream.
3, compose () executes immediately when you create the Observable stream, as if you had written the operators inline. FlatMap () executes when its onNext () are called, each time it is called. In other words, FLATMAP () transforms each item, whereas compose () transforms the whole stream.
FlatMap () is necessarily less efficient because it have to create a new Observable every time OnNext () is called. Compose () operates on the stream as it is.
If you want to replace some operators with reusable code, use compose (). FlatMap () has many uses and this is not one of the them.
Referenced from: http://blog.danlew.net/2015/03/02/dont-break-the-chain/
To put it simply:
1, compose is affecting the entire stream, and Flatmap is only the part that affects its own transformation.
2. Flatmap is executed after calling next (), while compose is executed directly.
3, Flatmap in next () after the execution will create a observable object (for the next operation to form a chain structure), and compose more like stitching to the top of the stream, a one-time execution, so the relative compose efficiency a bit higher.
This article is code: http://download.csdn.net/detail/jdsjlzx/9529124
Rxjava memory leak resolution in Android and Rxjava package