RxLifecycle源碼分析

隨着RxJava及RxAndroid的逐漸推廣,使用者越來越多,但是有一個問題,RxJava的使用不當極有可能會導致內存泄漏

目前網上對RxJava的內存泄漏有幾種方案:

1、RxLifecycle

2、AutoDispose

3、自己封裝,手動爲RxJava的每一次訂閱進行控制,在指定的時機進行取消訂閱

個人對RxLifecycle使用比較多,簡單直接,並且能夠在Activity/Fragment容器的指定生命週期取消訂閱

此處不對AutoDispose作分析,原理大致相同

 

1、依賴並使用RxLifecycle

  1. 1、首先在build.gradle文件中添加依賴
compile 'com.trello.rxlifecycle2:rxlifecycle:2.2.1'
compile 'com.trello.rxlifecycle2:rxlifecycle-android:2.2.1'
compile 'com.trello.rxlifecycle2:rxlifecycle-components:2.2.1'
  1. 2、配置Activity/Fragment容器

Activity/Fragment需繼承其中的RxActivity/RxFragment

代碼如下:

public abstract class BaseActivity extends RxActivity{
   
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        // TODO Auto-generated method stub
        super.onCreate(savedInstanceState);
        setContentView(initActivityLayoutID());
        initUI();
        test();
    }

    /**
     * 初始化Activity的佈局ID
     */
    protected abstract int initActivityLayoutID();

    /**
     * 初始化UI
     */
    protected abstract void initUI();

 
    @Override
    public LifecycleProvider getLifecycleProvider() {
        return this;
    }


    private void test(){
       // 當執行onDestory()時, 自動解除訂閱
        Observable.interval(1, TimeUnit.SECONDS)
            .doOnDispose(new Action() {
                @Override
                public void run() throws Exception {
                    Log.i(TAG, "Unsubscribing subscription from onCreate()");
                }
            })
            .compose(getLifecycleProvider())
            .subscribe(new Consumer<Long>() {
                @Override
                public void accept(Long num) throws Exception {
                    Log.i(TAG, "Started in onCreate(), running until onDestory(): " +      num);
                }
            });

        }
}

只需要三步:依賴、繼承、compose操作符,即可完成在容器的指定生命週期內,RxJava的自動取消訂閱。

2、分析原理(以RxActivity爲例)

2.1、RxActivity 

public abstract class RxActivity extends Activity implements LifecycleProvider<ActivityEvent> {

    //釋放訂閱前最後一個數據和訂閱後接收到的所有數據
    private final BehaviorSubject<ActivityEvent> lifecycleSubject = BehaviorSubject.create();

    @Override
    @NonNull
    @CheckResult
    public final Observable<ActivityEvent> lifecycle() {
        return lifecycleSubject.hide();
    }

    
    @Override
    @NonNull
    @CheckResult
    public final <T> LifecycleTransformer<T> bindUntilEvent(@NonNull ActivityEvent event) {
        return RxLifecycle.bindUntilEvent(lifecycleSubject, event);
    }

    //實際上返回了一個LifecycleTransformer
    @Override
    @NonNull
    @CheckResult
    public final <T> LifecycleTransformer<T> bindToLifecycle() {
        return RxLifecycleAndroid.bindActivity(lifecycleSubject);
    }

    //Activity不同的生命週期,BehaviorSubject對象會發射對應的ActivityEvent
    @Override
    @CallSuper
    protected void onCreate(@Nullable 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();
    }
}

關於RxJava 中Subject裏的BehaviorSubject原理,這個BehaviorSubject會在不同的生命週期發射不同的ActivityEvent,比如在onCreate()生命週期發射ActivityEvent.CREATE,在onStop()發射ActivityEvent.STOP

 

2.2、LifecycleTransformer

public final class LifecycleTransformer<T> implements ObservableTransformer<T, T>,
                                                      FlowableTransformer<T, T>,
                                                      SingleTransformer<T, T>,
                                                      MaybeTransformer<T, T>,
                                                      CompletableTransformer
{
    final Observable<?> observable;

    LifecycleTransformer(Observable<?> observable) {
        checkNotNull(observable, "observable == null");
        this.observable = observable;
    }

    @Override
    public ObservableSource<T> apply(Observable<T> upstream) {
        //當observable爲true是終止
        return upstream.takeUntil(observable);
    }

關於takeUntil原理

3、回過頭看bindToLifecycle,本質上RxActivity 中的BehaviorSubject成員變量(它本身就是一個Observable)!

public abstract class RxActivity extends Activity implements LifecycleProvider<ActivityEvent> {

    private final BehaviorSubject<ActivityEvent> lifecycleSubject = BehaviorSubject.create();

 
    @Override
    @NonNull
    @CheckResult
    public final <T> LifecycleTransformer<T> bindToLifecycle() {
        return RxLifecycleAndroid.bindActivity(lifecycleSubject);
    }

3.1、RxLifecycleAndroid

public class RxLifecycleAndroid {

    ***省略代碼
 @NonNull
    @CheckResult
    public static <T> LifecycleTransformer<T> bindActivity(@NonNull final Observable<ActivityEvent> lifecycle) {
        return bind(lifecycle, ACTIVITY_LIFECYCLE);
    }

    ***省略代碼

 // Figures out which corresponding next lifecycle event in which to unsubscribe, for Activities
    private static final Function<ActivityEvent, ActivityEvent> ACTIVITY_LIFECYCLE =
        new Function<ActivityEvent, ActivityEvent>() {
            @Override
            public ActivityEvent apply(ActivityEvent lastEvent) throws Exception {
                switch (lastEvent) {
                    case CREATE:
                        return ActivityEvent.DESTROY;
                    case START:
                        return ActivityEvent.STOP;
                    case RESUME:
                        return ActivityEvent.PAUSE;
                    case PAUSE:
                        return ActivityEvent.STOP;
                    case STOP:
                        return ActivityEvent.DESTROY;
                    case DESTROY:
                        throw new OutsideLifecycleException("Cannot bind to Activity lifecycle when outside of it.");
                    default:
                        throw new UnsupportedOperationException("Binding to " + lastEvent + " not yet implemented");
                }
            }
        };

}

    ***省略代碼


}

3.2、RxLifecycle

public class RxLifecycle {

    ***省略代碼
 @Nonnull
    @CheckReturnValue
    public static <T, R> LifecycleTransformer<T> bind(@Nonnull Observable<R> lifecycle,
                                                      @Nonnull final Function<R, R> correspondingEvents) {
        checkNotNull(lifecycle, "lifecycle == null");
        checkNotNull(correspondingEvents, "correspondingEvents == null");
        return bind(takeUntilCorrespondingEvent(lifecycle.share(), correspondingEvents));
    }

    private static <R> Observable<Boolean> takeUntilCorrespondingEvent(final Observable<R> lifecycle,
                                                                       final Function<R, R> correspondingEvents) {
        return Observable.combineLatest(
            lifecycle.take(1).map(correspondingEvents),
            lifecycle.skip(1),
            new BiFunction<R, R, Boolean>() {
                @Override
                public Boolean apply(R bindUntilEvent, R lifecycleEvent) throws Exception {
                    return lifecycleEvent.equals(bindUntilEvent);
                }
            })
            .onErrorReturn(Functions.RESUME_FUNCTION)
            .filter(Functions.SHOULD_COMPLETE);
    }
}

最終發現是調用combineLatest方法,逐步分析一下

1、lifecycle.take(1)指的是最近發射的事件,比如說我們在onCreate()中執行了bindToLifecycle,那麼lifecycle.take(1)指的就是ActivityEvent.CREATE,經過map(correspondingEvents),這個map中傳的函數就是 RxLifecycleAndroid中的ACTIVITY_LIFECYCLE。

也就是說,lifecycle.take(1).map(correspondingEvents)實際上是返回了 CREATE 對應的事件 DESTROY ,它意味着本次訂閱將在Activity的onDestory進行取消

2、lifecycle.skip(1)就簡單了,除去第一個保留剩下的,以ActivityEvent.Create爲例,這裏就剩下:

ActivityEvent.START
ActivityEvent.RESUME
ActivityEvent.PAUSE
ActivityEvent.STOP
ActivityEvent.DESTROY

3、第三個參數 意味着,lifecycle.take(1).map(correspondingEvents)的序列和 lifecycle.skip(1)進行combine,形成一個新的序列:

false,false,fasle,false,true

即是說,當Activity走到onStart生命週期時,爲false,這次訂閱不會取消,直到onDestroy,爲true,訂閱取消

 

4、而後的onErrorReturn和filter是對異常的處理和判斷是否應該結束訂閱:

//異常處理
    static final Function<Throwable, Boolean> RESUME_FUNCTION = new Function<Throwable, Boolean>() {
        @Override
        public Boolean apply(Throwable throwable) throws Exception {
            if (throwable instanceof OutsideLifecycleException) {
                return true;
            }
            Exceptions.propagate(throwable);
            return false;
        }
    };
    //是否應該取消訂閱,可以看到,這依賴於上游的boolean
    static final Predicate<Boolean> SHOULD_COMPLETE = new Predicate<Boolean>() {
        @Override
        public boolean test(Boolean shouldComplete) throws Exception {
            return shouldComplete;
        }
    };

 

至此對RxLifecycle已經很清晰!!

關於take原理

關於Skip原理

關於combineLatest原理

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章