記使用RxJava保存byte[]到文件,遇到的內存泄漏問題

前言

最近寫一個頁面內會屢次拍照並保存的需求.連拍屢次發現內存泄漏. 找緣由花了很多時間.記錄下來.java

問題:

Paste_Image.png

Paste_Image.png

將byte[]保存爲文件.明明已經關閉了流.數組

然而一頓連拍後,內存監控卻大吃一驚.bash

Paste_Image.png

點小黃車gc也很差使.... spa

Paste_Image.png

內存分析:

Paste_Image.png

查看內存報告.很明顯,byte[]數組泄漏了.

Paste_Image.png

找到內存佔用很大的byte[]code

Paste_Image.png

什麼?cdn

Paste_Image.png

很明顯,Rxjava引用了這個數組,而且這個observerable沒被回收.server

先從Rxjava入手了.看源碼blog

Paste_Image.png

這裏保存了byte[]引用.ip

那麼就是Observable訂閱沒取消咯.內存

什麼?不是走了onCompleted()後就會釋放嗎?

具體緣由:

使用CompositeSubscription添加了subscribe
Subscription subscribe = Observable.just(data)
  ``````//具體邏輯省略
  mCompositeSubscription.add(subscribe);
複製代碼
  • 由於CompositeSubscription添加了Subscription,onCompleted()不會取消訂閱. 必須經過CompositeSubscription.unsubscribe().然而使用了這個方法後CompositeSubscription就不能再添加訂閱了

解決辦法:

1.使用clear()方法,而不是unsubscribe()
mCompositeSubscription.clear();
  Subscription subscribe = Observable.just(data)
   ````//省略
複製代碼
2.不使用CompositeSubscription.(不推薦)
//mCompositeSubscription.add(subscribe);
複製代碼

總結

  • CompositeSubscription.clean(),取消添加的全部訂閱,能繼續添加訂閱
  • CompositeSubscription.unsubscribe(),取消全部訂閱,不能繼續添加訂閱
  • 使用CompositeSubscription添加了訂閱後,onCompleted()執行後沒法徹底解除訂閱(ps:其實在CompositeSubscription.add()的時候已經調用了.)
雖然問題解決很簡單.可是找緣由還挺麻煩的.
1.覺得bitmap沒回收.使用弱引用發現依然沒效果.
2.查到byte保存爲文件時出的問題.
3.查到RxJava轉換操做會保存引用.再
4.分析猜是沒取消訂閱.
5.發現確實是CompositeSubscription的問題
複製代碼

但願以上找bug的過程能給各位帶來幫助和思路.


您的喜歡與回覆是我最大的動力-_-(ps:還不是爲了出名,爲了吸粉)

交流羣:493180098,這是個不多吹水,有人解決問題的羣.

相關文章
相關標籤/搜索