内存泄露,简称OOM(OutOfMemory)。区别于Web开发、PC端程序开发,Android程序开发有一个很大的限制:设备资源有限。当Android应用程序处理较大内存资源如图片、音乐、视频等多媒体资源时,在资源数量过多、处理时间太久的情况下,很容易耗尽设备资源,此时,内存泄露就发生了。
那么,什么样的Android程序容易引起OOM呢?以下来自我开发Android应用程序的总结和网上收集的资料。
1.bitmap处理不当引起的OOM
Bitmap占用资源大,很容易吃完内存,这也是内存溢出问题里最为常见的问题。
为了有效优化处理Bitmap带给我们的内存问题,我们应当注意以下几点。
a.及时销毁
用完Bitmap后,要及时recycle。recycle不能保证立即释放Bitmap,但会给虚拟机一个暗示:"该图片可以释放了"。
if(!bitmapObject.isRecycle()){
bitmapObject.recycle();
}
b.适时使用软引用
回收bitmap时调用recycle()方法,该方法只能在bitmap放弃所有引用的情况下才能回收,否则会报使用已回收的bitmap的错误。然而我们使用bitmap时,大多数时间是创建的局部变量,引用这些bitmap的控件却是全局的,或者说有更长的生命周期,所以回收bitmap要在控件不再引用该资源的情况下调用recycle()方法,这也是经常调用recycle()方法不成功而放弃回收bitmap的原因。另外,有些时候,我们使用Bitmap后没有保留对它的引用,因此就无法调用Recycle函数。这时候巧妙的运用软引用,可以使Bitmap在内存快不足时得到有效的释放。
private class MyAdapter extends BaseAdapter {
private ArrayList> mBitmapRefs = new ArrayList>();
public View getView(int i, View view, ViewGroup viewGroup) {
View newView = null;
if(view != null) {
newView = view;
} else {
newView =(View)mInflater.inflate(R.layout.image_view, false);
}
Bitmap bitmap = BitmapFactory.decodeFile(mValues.get(i).fileName);
mBitmapRefs.add(new SoftReference(bitmap)); //此处加入ArrayList
((ImageView)newView).setImageBitmap(bitmap);
return newView;
}
}
c.适时减小生成的bitmap占用空间
当要显示的区域很小,没必要将整个图片都加在出来,只需要加载一个缩小过的图片,可以设置适当的采样率,就可以有效减小占用的内存。
private ImageView preview;
BitmapFactory.Options options = new BitmapFactory.Options();
options.inSampleSize = 2;//图片宽高都为原来的二分之一,即图片为原来的四分之一
Bitmap bitmap = BitmapFactory.decodeStream(cr.openInputStream(uri), null, options);
preview.setImageBitmap(bitmap);