1:首先媒区,我們來說一下為什么會有OOM(內(nèi)存溢出)
因為安卓系統(tǒng)的APP每個進(jìn)程或虛擬機有最大內(nèi)存限制,一旦超過這個限制就會拋出OOM異常已脓,跟手機剩余內(nèi)存是否充足沒有太大關(guān)系珊楼。
2 :很多人會認(rèn)為內(nèi)存泄露跟內(nèi)存溢出沒什么區(qū)別,這是錯誤的度液,內(nèi)存泄露跟內(nèi)存溢出根本就是兩碼事厕宗,接下來就說說內(nèi)存泄露和內(nèi)存溢出的區(qū)別及聯(lián)系
2.1? ??二者區(qū)別
? ????????1、內(nèi)存泄漏memory leak?:是指程序在申請內(nèi)存后堕担,無法釋放已申請的內(nèi)存空間已慢,一次內(nèi)存泄漏似乎不會有大的影響,但內(nèi)存泄漏堆積后的后果就是內(nèi)存溢出霹购。?
? ? ? ? ? 2佑惠、內(nèi)存溢出 out of memory?:指程序申請內(nèi)存時,沒有足夠的內(nèi)存供申請者使用齐疙,或者說膜楷,給了你一塊存儲int類型數(shù)據(jù)的存儲空間,但是你卻存儲long類型的數(shù)據(jù)贞奋,那么結(jié)果就是內(nèi)存不夠用赌厅,此時就會報錯OOM,即所謂的內(nèi)存溢出。?
2.1????二者的關(guān)系
內(nèi)存泄漏的堆積最終會導(dǎo)致內(nèi)存溢出
內(nèi)存溢出就是你要的內(nèi)存空間超過了系統(tǒng)實際分配給你的空間轿塔,此時系統(tǒng)相當(dāng)于沒法滿足你的需求特愿,就會報內(nèi)存溢出的錯誤。
內(nèi)存泄漏是指你向系統(tǒng)申請分配內(nèi)存進(jìn)行使用(new)勾缭,可是使用完了以后卻不歸還(delete)揍障,結(jié)果你申請到的那塊內(nèi)存你自己也不能再訪問(也許你把它的地址給弄丟了),而系統(tǒng)也不能再次將它分配給需要的程序俩由。就相當(dāng)于你租了個帶鑰匙的柜子亚兄,你存完東西之后把柜子鎖上之后,把鑰匙丟了或者沒有將鑰匙還回去采驻,那么結(jié)果就是這個柜子將無法供給任何人使用审胚,也無法被垃圾回收器回收,因為找不到他的任何信息礼旅。
內(nèi)存溢出:一個盤子用盡各種方法只能裝4個果子膳叨,你裝了5個,結(jié)果掉倒地上不能吃了痘系。這就是溢出菲嘴。比方說棧,棧滿時再做進(jìn)棧必定產(chǎn)生空間溢出,叫上溢龄坪,椪汛疲空時再做退棧也產(chǎn)生空間溢出,稱為下溢健田。就是分配的內(nèi)存不足以放下數(shù)據(jù)項序列,稱為內(nèi)存溢出烛卧。說白了就是我承受不了那么多,那我就報錯妓局。
3:很多人會問? 有Gc垃圾回收機制了总放,為什么還會有內(nèi)存溢出呢,
Android的Gc垃圾回收機制會按照特定的算法來回收不使用的資源好爬,但是GC一般回收的是沒用的對象內(nèi)存或軟引用資源局雄。
使用軟引用圖片資源在一定程度上可以避免OOM(軟引用類似于生活上可有可無的物品,如果內(nèi)存足夠,垃圾回收機制就不會回收他存炮,如果內(nèi)存空間不足的話炬搭,就會回收這些對象)
4:內(nèi)存溢出造成的影響
應(yīng)用卡頓:泄漏的內(nèi)存影響了GC的內(nèi)存分配,過多的內(nèi)存泄漏會影響應(yīng)用的執(zhí)行率
5:關(guān)于內(nèi)存溢出的原因及簡單的解決方案穆桂,以下幾個是我的簡單總結(jié)宫盔,當(dāng)然,肯定也有不足:
1.查詢完數(shù)據(jù)庫充尉,數(shù)據(jù)庫的cursor(游標(biāo))沒有關(guān)閉。(原因)
措施:保證Cursor占用的內(nèi)存被及時的釋放掉衣形,而不是等待GC來處理
2.未關(guān)閉InputStream/OutputStream驼侠。(原因)
措施:這個就不多說了,我們操作完輸入輸出流都要關(guān)閉流
3.Bitmap使用后未調(diào)用recycle()谆吴。(原因)
措施:第一倒源、及時的銷毀。
????????????第二句狼、設(shè)置一定的采樣率笋熬。
4.Context泄漏。(原因)
措施:? ? 第一腻菇、將線程的內(nèi)部類胳螟,改為靜態(tài)內(nèi)部類。并且注意第二條筹吐。
? ? ? ? ? ? ? ? 第二糖耸、在線程內(nèi)部采用弱引用保存Context引用。
5.static關(guān)鍵字等丘薛。(原因)
措施:第一嘉竟,應(yīng)該盡量避免static成員變量引用資源耗費過多的實例,比如Context。
? ? ????????第二舍扰、Context盡量使用Application Context倦蚪,因為Application的Context的生命周期比較長,? ? ? ?????????????引用它不會出現(xiàn)內(nèi)存泄露的問題边苹。
? ????????? 第三陵且、使用WeakReference代替強引用。比如可以使用WeakReference mContextRef;
6勾给、圖片過大導(dǎo)致 OOM(原因)
措施:方法 1: 等比例縮小圖片
????????????方法 2:對圖片采用軟引用滩报,及時地進(jìn)行 recyle()操作