Android有效解决加载大图片时内存溢出的问题

标签: android 有效 加载 | 发表时间:2013-09-12 00:16 | 作者:scry5566
出处:http://blog.csdn.net
         尽量不要使用setImageBitmap或setImageResource或BitmapFactory.decodeResource来设置一张大图,
因为这些函数在完成decode后,最终都是通过java层的createBitmap来完成的,需要消耗更多内存。
         因此,改用先通过BitmapFactory.decodeStream方法,创建出一个bitmap,再将其设为ImageView的 source,
decodeStream最大的秘密在于其直接调用JNI>>nativeDecodeAsset()来完成decode,无需再使用java层的createBitmap,从而节省了java层的空间。
如果在读取时加上图片的Config参数,可以跟有效减少加载的内存,从而跟有效阻止抛out of Memory异常
另外,decodeStream直接拿的图片来读取字节码了, 不会根据机器的各种分辨率来自动适应, 
使用了decodeStream之后,需要在hdpi和mdpi,ldpi中配置相应的图片资源, 

否则在不同分辨率机器上都是同样大小(像素点数量),显示出来的大小就不对了。

       下面附上我个人写代码:

/**
	 * Funciton:按指定长宽并以最省内存的方式读取本地资源的图片(通过C层API加载图片,消耗的是C层内存,而不会消耗JAVA虚拟机的内存)。
	 * <font color="red">【注意】此方法应该在以下非常情况下使用:应用内存非常吃紧或者图片过大时可使用此方法。
	 * 使用此方法的可能后果:会有一定几率造成应用崩溃,请慎用,</font>
	 * 
	 * @param context
	 * @param resId
	 * @return
	 */
	public static Bitmap decodeStreamWithLowMemory(Context context, int resId,
			int reqWidth, int reqHeight) {
		// First decode with inJustDecodeBounds=true to check dimensions
		BitmapFactory.Options options = new BitmapFactory.Options();
		options.inJustDecodeBounds = true;
		BitmapFactory.decodeResource(context.getResources(), resId, options);

		// Calculate inSampleSize
		options.inSampleSize = calculateInSampleSize(options, reqWidth, reqHeight);
		// Decode bitmap with inSampleSize set
		options.inJustDecodeBounds = false;

		// Bitmap.Config.ALPHA_8,Bitmap.Config.ARGB_4444,Bitmap.Config.RGB_565
		// 设置这几个参数效果都差不多,确实相当省内存啊,而且还跟原图清晰度相当
		options.inPreferredConfig = Bitmap.Config.ARGB_8888;
		options.inPurgeable = true;
		options.inInputShareable = true;

		// 获取资源图片
		InputStream is = context.getResources().openRawResource(resId);
		return BitmapFactory.decodeStream(is, null, options);
	}

/**
	 * Funciton:以最省内存的方式读取本地资源的图片; <font color="red">【注意】:
	 * 此方法以BitmapFactory.decodeResource ()去加载图片,使用此方法每次会创建一个新的Btimap对象,
	 * 而不会共享应用res中创建的Btimap资源,因此要即时回收旧图片,以免造成内存泄露。</font>
	 * 
	 * @param context
	 * @param resId
	 * @return
	 */
	public static Bitmap decodeResourceWithLowMemory(Context context, int resId) {
		BitmapFactory.Options opt = new BitmapFactory.Options();
		// Bitmap.Config.ALPHA_8,Bitmap.Config.ARGB_4444,Bitmap.Config.RGB_565
		// 设置这几个参数效果都差不多,确实相当省内存啊,而且还跟原图清晰度相当
		opt.inPreferredConfig = Bitmap.Config.RGB_565;
		opt.inPurgeable = true;
		opt.inInputShareable = true;
		//
		return BitmapFactory.decodeResource(context.getResources(), resId, opt);
	}




作者:scry5566 发表于2013-9-11 16:16:51 原文链接
阅读:4 评论:0 查看评论

相关 [android 有效 加载] 推荐:

Android有效解决加载大图片时内存溢出的问题

- - CSDN博客推荐文章
         尽量不要使用setImageBitmap或setImageResource或BitmapFactory.decodeResource来设置一张大图,. 因为这些函数在完成decode后,最终都是通过java层的createBitmap来完成的,需要消耗更多内存.          因此,改用先通过BitmapFactory.decodeStream方法,创建出一个bitmap,再将其设为ImageView的 source,.

Android 网页加载完成ProgressDialog运用

- - CSDN博客推荐文章
      "正在进入网页,请稍后.   // 设置视图客户端. 作者:gongzibai 发表于2012-7-23 0:31:58 原文链接. 阅读:13 评论:0 查看评论.

Android 之 Activity的加载模式

- - 移动开发 - ITeye博客
         加载模式决定以哪种方式启动一个跳转到原来某个Activity实例;.         在Android 开发中,activity 之间的跳转可能需要有多种方式,有时是普通的生成一个新实例,有时希望跳转到原来某个activity实例,而不是生成大量的重复的activity;. 3)  加载模式的种类:.

DexClassLoader 实现 Android 插件加载

- - RincLiu.com
Java 中的 ClassLoader:. Java 中 ClassLoader 用于动态加载 Class 到 JVM,包含. BootstrapClassLoader(C++ 编写,用于加载系统核心类)、 ExtClassLoader(用于加载 lib/ext/ 目录的扩展 API)、 AppClassLoader(加载 CLASSPATH 目录下的类).

android WebView, WebChromeClient和WebViewClient加载网页基本用法

- - CSDN博客推荐文章
WebView, WebChromeClient和WebViewClient加载网页基本用法.  webview是android中的浏览器控件,在一些手机应用中常会用到b/s模式去开发应用,这时webview的强大功能就会显示出来.  1、webview的几点设置.  权限设置:.AndroidManifest.xml中必须使用许可"android.permission.INTERNET",否则会出Web page not available错误.

android 图片加载和缓存开源项目 Picasso

- - 移动开发 - ITeye博客
Picasso – Android系统的图片下载和缓存类库. Picasso 是Square开源的一个用于Android系统下载和缓存图片的项目. 该项目和其他一些下载图片项目的主要区别之一是:使用4.0+系统上的HTTP缓存来代替磁盘缓存. Picasso 的使用是非常简单的,例如:. 处理Adapter中的 ImageView 回收和取消已经回收ImageView的下载进程.

美团Android DEX自动拆包及动态加载简介

- - 美团技术团队
作为一个android开发者,在开发应用时,随着业务规模发展到一定程度,不断地加入新功能、添加新的类库,代码在急剧的膨胀,相应的apk包的大小也急剧增加, 那么终有一天,你会不幸遇到这个错误:. 生成的apk在android 2.3或之前的机器上无法安装,提示INSTALL_FAILED_DEXOPT.

FaceBook推出的Android图片加载库-Fresco

- - CSDN博客推荐文章
在Android设备上面,快速高效的显示图片是极为重要的. 过去的几年里,我们在如何高效的存储图像这方面遇到了很多问题. 图片太大,但是手机的内存却很小. 每一个像素的R、G、B和alpha通道总共要占用4byte的空间. 如果手机的屏幕是480*800,那么一张屏幕大小的图片就要占用1.5M的内存.

Android 动态加载技术三个关键问题详解

- - 移动开发 - ITeye博客
关注微信号:javalearns   随时随地学Java. 动态加载技术(也叫插件化技术)在技术驱动型的公司中扮演着相当重要的角色,当项目越来越庞大的时候,需要通过插件化来减轻应用的内存和CPU占用,还可以实现热插拔,即在不发布新版本的情况下更新某些模块. 动态加载是一项很复杂的技术,这里主要介绍动态加载技术中的三个基础性问题,至于完整的动态加载技术的实现请参考笔者发起的开源插件化框架DL:.

Android 视频缩略图的缓存机制和异步加载

- - 移动开发 - ITeye博客
关注微信号:javalearns   随时随地学Java. 在这次的工作开发项目中,涉及到一个视频缩略图的视频列表;这个在大家看来,制作视频缩略图就是两行代码就搞定的事. 确实是这样的,百度一下,每个 帖子都知道制作视频缩略图的方法,在这里确实也是一样的,但是我要实现的是让缩略图 在ListView上显示,而且不会出现卡顿,其实也不是特别难,确实很实用;.