加载大图片时,出现的OOM异常,以及处理OOM异常的方法

首先 , 得明白什么是 OOM异常, 即OutOfMemory异常,内存溢出导致的.
1,  如何计算出 加载图片进内存时的大小? 
在 Android中 , 加载一张图片时,比如 一张 2560X1920的高清图片,大小是  2560 x 1920 x 4 / 1024 / 1024  = 18.75 M,
android 中加载图片时,因为用的是argb处理, a 指透明度,r 指红色,g 指绿色, b 指蓝色,每个占8个bit即一个byte.所以,一个图片的像素是 4个字节.


2,为什么会出现 OOM异常?
上面已经计算出了图片加载进内存时的大小是 18.75 M,而我的这个模拟器上的虚拟机 的 堆内存 VM Heap只有 16M,所以就OOM了. 


3,处理OOM 异常的方法。
处理OOM异常的方法有很多,我这里只列出最简单的一种
先介绍下思路 : 
                              1,得到图片的宽和高
                               2,得到屏幕的宽和高(因为整个屏幕的像素都加载进内存,也不会造成内存溢出)
                               3,得到 图片的宽和屏幕宽(或控件宽)的比值,图片高和屏幕高(或控件高)的比值,选择比值大的那个
                                4,设置 Option的inSampleSize 属性来缩小图片
//这是一个按钮的点击事件,这样做的话,图片过大就会出现OOM异常
public void onClick(View view){
        //在这一步,将图片加载进内存时,就已经出OOM了
        Bitmap bitmap = BitmapFactory.decodeFile("/storage/sdcard/fury-006.jpg");
        imageView.setImageBitmap(bitmap);
}


//处理后的情况则是

    public void onClick(View v)
    {
    	Options option = new Options();
    	/**如果该属性设为true的话,那么下面的decodeFile函数就会返回一个不带图片的bitmap对象,
    	 * 并且,图片的实际宽高也会被映射到option对象中
    	 */
    	option.inJustDecodeBounds = true;
    	BitmapFactory.decodeFile("/storage/mnt/sdcard/fury-009.jpg", option); 
    	//获得图片的实际宽高
    	int height = option.outHeight;
    	int width = option.outWidth;
    	//获得屏幕的宽高
    	WindowManager wm = this.getWindowManager();
    	int screen_height = wm.getDefaultDisplay().getHeight();
    	int screen_width = wm.getDefaultDisplay().getWidth();
    	
    	//得到图片的宽高与屏幕或者ImageView控件大小的比值,选取合适的值
    	int scale = 1;
    	int sx = width/screen_width;
    	int sy = height/screen_height;
    	if(sx > sy && sx >= 1)
    	{
    		scale = sx;
    	}else if(sy > sx && sy >= 1)
    	{
    		scale = sy;
    	}
    	//如果该值设为false,那么就会返回带图片的Bitmap对象
    	option.inJustDecodeBounds = false;
    	option.inSampleSize = scale;//该值大于1的话,就会把图片按比例缩小,得到一个bitmap对象
    	Bitmap bitmap = BitmapFactory.decodeFile("/storage/sdcard/fury-009.jpg", option); 
    	
    	imageView.setImageBitmap(bitmap);
    }
    
}

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值