Android Bitmap内存管理,解决内存溢出问题(1)之自定义BitmapDrawable

【零基础入门哈希签名架构,从Lamport到SPHINCS+】第二集 哈希签名树 Merkle Tree Authentication 在第一集中,我们一直忽略了一个问题。设想一下,假如有一个Hacker(黑客),在截获到Sender发送给Receiver的公钥之后,把这个公钥改成Hacker自己的公钥,然后再发给Receiver,那么Receiver就会误认为这是Sender的公钥。所以我们之前所说放方案,其安全性都需要建立在一个前提下:Receiver需要确认公钥确实是Sender发出的。 阅读详情

在Android 2.3.3或者更低版本下的时候,对于释放Bitmap的内存调用recycle()方法是必要的。否则在加载大量Bitmap的时候很容易就造成 OutOfMemoryError 。recycle()能够及时的释放Bitmap内存。

注意:只有在不用Bitmap的时候才能调用recycle(),否则会造成Canvas: trying to use a recycled bitmap问题。


内存管理的全部实现有点复杂,但是把复杂的问题拆分开来作就非常简单了,在本章中只是实现能够自己释放内存的


BitmapDrawable。代码如下:

public static final String	TAG					= "RecyclingBitmapDrawable";

	/**
	 * 正在使用(显示)的计数
	 * */
	private int					mDisplayRefCounts	= 0;

	/**
	 * 正在被缓存的计数
	 * */
	private int					mCacheRefCounts		= 0;

	/**
	 * 是否已经被显示过了
	 * */
	private boolean				mHasDisplay			= false;

	public RecyclingBitmapDrawable(Resources res, Bitmap bitmap) {
		super(res, bitmap);
		// TODO Auto-generated constructor stub
	}

	/**
	 * 
	 * 设置BitmapDrawable是否正在显示,如果显示这里传入true,如果不再显示了这里传入 false
	 * 
	 * @param isDisplayed
	 *            是否显示
	 * */
	public void setIsDisplayed(boolean isDisplayed) {
		synchronized (this) { // 保持同步,防止多个线程修改数据时造成 Canvas: trying to use a
								// recycled bitmap或者 OutOfMemoryError
			if (isDisplayed) {
				mDisplayRefCounts++;
				mHasDisplay = true;
			} else {
				mDisplayRefCounts--;

			}
		}

		// 这个不需要同步
		checkState();
	}

	/**
	 * 设置BitmapDrawable是否正在被缓存,如果被缓存了这里传入true,否则传入 false
	 * */
	public void setIsCached(boolean isCached) {
		synchronized (this) {
			if (isCached) {
				mCacheRefCounts++;
			} else {
				mCacheRefCounts--;
			}
		}
		checkState();
	}

	// 检测显示和缓存状态,如果计数都为0的话,就释放Bitmap
	private void checkState() {
		synchronized (this) {
			if (mDisplayRefCounts <= 0 && mCacheRefCounts <= 0 && mHasDisplay && hasVildBitmap()) {
				if (BuildConfig.DEBUG) {
					System.out.println(TAG + "--" + "释放不再使用的Bitmap");
					getBitmap().recycle();
				}
			}
		}
	}

	// 检测Bitmap是否可用,Bitmap不能为空,并且没有被释放
	private boolean hasVildBitmap() {
		synchronized (this) {
			Bitmap bitmap = getBitmap();

			return bitmap != null && !bitmap.isRecycled();
		}
	}


在这里不得不说下在 Android2.3.3或更高版本上的Bitmap内存处理,为了更有效的利用Bitmap的内存,要充分利

用 BitmapFactory.Options.inBitmap 这个字段,具体内容查看http://blog.youkuaiyun.com/hello_tree/article/details/11732293


在这里总结下android不同版本对于图片存储和释放的不同之处:


①在过去通过 SoftReference或者WeakReference来缓存Bitmap,但是从Android 2.3(API Level 9)开始,就不推荐

使用了,因为从2.3开始垃圾回收器会非常积极的回收 soft/weak 引用,这使得这样缓存相当无效。


②在Android3.0(API Level 11)之前,bitmap的像素数据是存储在 in native memory 本地的,是和Bitmap自己分

开存储的,Bitmap存储在 Dalvik heap中,Bitmap的像素数据(在 native memeory中)的释放是不可预见的,这

可能导致程序内存不够从而崩溃。在Android 3.0(API Level 11)开始,Bitmap的像素数据和相关的Bitmap一块存储

在 Dalvik heap中。


③在Android 3.0(API Level 11)之前,如果加载大量bitmap数据在你的app 中时,应该在不用Bitmap的时候调用

recycle()方法,recycle()方法允许app尽快的回收内存(由于在 3.0之前Bitmap的后台像素数据和Bitmap是分开存

储的,并且后台数据的释放是不可预见的,所以通过手动调用Bitmap的recycle()方法来释放内存)。


④在Android 3.0(API Level 11)和之后的版本中,由于bitmap的后台像素数据和它本身一块存储在虚拟机堆(Dalvik

 heap)中,所

以不用手动调用Bitmap的recycle()方法,当没有引用指向Bitmap的时候,垃圾回收器会自动释放bitmap的内存。




STGCN实战:从零构建PyTorch时空图卷积网络预测城市交通流 本文详细介绍了如何使用PyTorch从零构建时空图卷积网络(STGCN)进行城市交通流预测。通过将交通网络建模为图结构,并融合时间卷积与空间图卷积,STGCN能有效捕捉交通流的时空依赖性。文章提供了从数据预处理、核心模块(TimeBlock与STGCNBlock)搭建、模型训练到实战技巧的完整指南,帮助开发者快速掌握这一前沿的交通速度预测技术。 阅读详情

相关推荐

el-table通过上下左右键移动光标

在Element Plus的el-table中包含el-input和el-select组件,要实现上下左右键控制光标位置,需要通过focus和blur跟踪判断当前是哪个el-input或el-select有焦点,当按键按下时,通过监听,计算下一个获取焦点元素的索引,通过focus方法将焦点切换至改元素。

秋思的博客 1350

图片内存溢出和图片压缩

1) 要及时回收Bitmap的内存 Bitmap类有一个方法recycle(),从方法名可以看出意思是回收。这里就有疑问了,Android系统有自己的垃圾回收机制,可以不定期的回收掉不使用的内存空间,当然也包括Bitmap的空间。那为什么还需要这个方法呢? Bitmap类的构造方法都是私有的,所以开发者不能直接new出一个Bitmap对象,只能通过BitmapFactory类的各种静态

小邓(Java) 2120

PCA9548实战:从硬件连接到Linux驱动的I2C扩展全解析

本文详细解析了PCA9548 I2C多路复用器从硬件连接到Linux驱动配置的全过程。涵盖硬件引脚连接、电源去耦、地址选择等关键设计要点,以及Linux驱动加载、设备树配置和应用层编程技巧,帮助开发者高效实现I2C总线扩展。

weixin_28726391的博客 410

Android系统中Bitmap是否有调用recycle方法的必要性

Bitmap有一个recycle方法,意思很简单,回收Bitmap的空间。但是我们知道java有自己的垃圾回收机制,所以为什么BitaMap还需要这样一个专门的回收方法呢? 无需调用bitmap的理由有: a. 垃圾回收会处理的; b. 当application关闭,process被杀掉,所有这个process占用的空间自然回归系统;    虽然Android有自己

findsafety的专栏 1614

深入解析反射式DLL注入:从原理到实战优化

本文深入解析反射式DLL注入技术,从原理到实战优化全面剖析。通过PE文件内存重构、反射加载器实现及免杀增强方案,展示如何绕过安全检测并提升性能。适用于红队行动、内网渗透等场景,是高级攻防对抗中的关键技术。

weixin_28339967的博客 404

YOLOv8/v9工业零件缺陷检测实战指南:从原理到产线部署

摘要:本文系统介绍基于YOLOv8/v9的工业零件缺陷检测技术,从工业质检背景与需求出发,详解缺陷检测原理、算法构建与模型训练,提供从数据集准备到移动端部署的全流程实操方案。包含多尺度检测、纹理分析等高级技术,适配工业相机的环境优化策略,以及完整质检系统代码实现。适合工业视觉领域新手与进阶开发者,助力快速构建高鲁棒性的缺陷检测系统。

专注于人工智能、软件开发、工控自动化、工厂数字化及智能化等领域,希望和大家共同进步! 1306

android Bitmap类方法属性 详细说明

(转:http://blog.youkuaiyun.com/ymangu666/article/details/37729109) 1.  BitMap类public void recycle()——回收位图占用的内存空间,把位图标记为Dead public final boolean isRecycled() ——判断位图内存是否已释放 public final int getWidth()——获取位图的...

weixin_34235457的博客 496

13、数据可视化与分组操作:Danfo.js 实战指南

本文深入介绍了如何使用 Danfo.js 进行数据可视化与分组操作。内容涵盖多种图表的创建与配置,如折线图、散点图、箱线图、小提琴图、直方图和柱状图,并结合 Plotly.js 实现丰富的交互式可视化效果。同时,详细讲解了数据聚合的‘分割-应用-组合’模式,包括分组数据、遍历分组、apply 方法及 agg 聚合操作,帮助开发者高效处理和分析结构化数据。适用于 Dnotebook、HTML 及主流前端框架的应用场景。

o1p2q3r的博客 99

Bitmap内存管理

在Android 2.3.3,使用recycle()来释放Bitmap占用的内存,但是你必须要等到该Bitmap不再使用时,才可以使用recyle()来释放Bitma占用的内存,否则的话会引起错误。 我们经常会使用到同一张图片,而Bitmap的创建和销毁是比较占用内存的开销的,所以我们可以自定义一个可复用的BitmapDrawable来管理Bitmap,并且赋予它两个变量,一个的mDisplay

Running&H的博客 978

视觉测量实战:C#上位机+OpenCVSharp 实现工业零件尺寸自动检测(精准像素级,工业级可落地)

本次开发的上位机界面遵循工业现场操作规范简洁、直观、按钮大、文字清晰、参数可视化调节,操作人员为车间工人/质检员,无需复杂操作,所有控件均为WinForms原生控件,拖拽即可完成布局本次实战完成了C#上位机+OpenCVSharp 工业零件尺寸自动检测系统的完整开发,这套方案是工业视觉测量的标准落地方案,适配95%的规则几何零件的尺寸检测场景,从五金件、塑胶件到电子元件,全覆盖无死角。测量效率提升100倍、精度提升10倍、无人工误差、可适配流水线实时检测。

这里只有干货:从 Modbus 通信到 MES 对接,从 YOLO 训练到工控机部署,带你搞定工业软件开发全流程。 849

Oracle EBS 如何处理MMT表错误-WIP 实体未定义或不具有期间余额项

错误说明:WIP 实体未定义或不具有期间余额项。(The wip entity is either not defined or does not have a period balance entry)由于工单的创建日期为4月份,工单的余额表记录的期间是4月份,而3月份工单余额表中没有记录。公司将上一个新的库存组织,有一部分测试的工单创建日期在4月份,而工单的发放日期、发料事务处理日期和完工事务处理日期均在3月份。1、关闭3月份库存会计期,待定事务处理存在未计成本物料/WMS。成本类型: PAC成本。

陈显平的专栏-Oracle EBS 652

android Recycled bitmap error

问题描述: 在部分机器上出现,Can't compress a recycled bitmap,而且还是偶现,要命啊... 代码片段,案发现场分析: Bitmap ret = Bitmap.createBitmap(bmpt, 0, 0, bmpt.getWidth(), bmpt.getHeight(), m, true); if(null != bmpt && !bmpt.i

u010674982的专栏 3437

使用 MATLAB/Simulink 构建一个基于FOC控制的PMSM矢量控制仿真模型

本教程详细介绍了基于Simulink的永磁同步电机(PMSM)磁场定向控制(FOC)仿真建模过程。主要内容包括:PMSM电机参数设置、Clarke/Park变换模块设计、电流环PID控制器构建、SVPWM调制实现等关键步骤。教程提供了完整的建模流程、参数配置建议和仿真调试方法,并给出了PID整定技巧和进阶优化方向。通过该模型,可深入理解PMSM矢量控制原理,掌握高性能电机控制系统的建模技术,为伺服系统、电动汽车驱动等应用领域提供仿真基础。教程还推荐了使用PIDTuner工具进行参数优化,并提出了加入负载扰动

amy_mhd的博客 644

Android内存管理试验——浅谈ImageView的Bitmap的使用

转自:http://blog.youkuaiyun.com/ztp800201/article/details/16830191

冷秋魂的专栏 7622

OV9734 DATASHEET,完整规格书

OV9734完整规格书,包括电气参数,尺寸规格,寄存器配置表等

文档:亲测可用解决vnc灰屏,黑屏,鼠标大黑叉情况

主要解决vnc-viewer灰屏,黑屏,鼠标大黑叉等现象,详细见文档。

【android 优化】ImageView的Bitmap的使用

原文地址:http://blog.renren.com/share/190558220/7583924873 Android内存管理试验——浅谈ImageView的Bitmap的使用(原创) 来源: 韩玮的日志 今天在项目中碰到了史无前例的内存泄漏问题,在大量使用Bitmap的Activity的中概率性出现如下错误: 07-13 13:17:20.534

代码碎片 1611

华为的C语言编程规范.pdf

华为技术有限公司内部技术规范。本规范制定了编写C语言程序的基本原则、规则和建议。从代码的清晰、简洁、可测试、安全、程序效率、可移植各个方面对C语言编程作出了具体指导。

bitmap时候内存溢出

很多人在android开发中都遇到了生成bitmap时候内存溢出,也就是out of memory(OOM)的问题,网上对这样的问题的的解决说法不一。笔者作为一个初级开发者,在这里向大家提供一种比较实用,比较易于理解的方法,这种方法不如一些高级开发者提出的方案来的深刻,但是也能帮助大家有效地解决问题。 废话不多说了,直接上代码。 Java代码   BitmapFact

lideguo1979的专栏 1086

SAP B1中文培訓教材_SDK

公司内部培训资料,对开发工具 ,DIAPI, UIAPI,Add-ON有详细解说

Bitmap释放

Bitmap没有及时释放的话经常会出现OOM错误。由于Bitmap占用的是底层C的内存,JVM的垃圾回收机制对他没有用。用完后必须显示的调用 recycle();告诉虚拟器该Bitmap没有用了,可以释放了,能后虚拟器才能在稍后的时候释放。   1.Bitmap变量 [java] view plaincopy Bitmap bit =

jonemill的专栏 876

Android处理图片报OOM的问题解决

当使用android的Drawable时,一开始我是用下面的方法实现的: Drawable.createFromStream(is, srcName);   但是经过调试每次程序都会crash掉,报OOM错误,错误都会打到上面这行代码,搞了老半天,发现BitmapFactory.decodeStream比Drawable.createFromStream好用,后者更占内存。下面是解决

Jack_Leonardo的博客 828

Android 那些你所不知道的Bitmap对象详解

转载请注明本文出自xiaanming的博客(http://blog.youkuaiyun.com/xiaanming/article/details/41084843),请尊重他人的辛勤劳动成果,谢谢! 我们知道Android系统分配给每个应用程序的内存是有限的,Bitmap作为消耗内存大户,我们对Bitmap的管理稍有不当就可能引发OutOfMemoryError,而Bitmap对象在不同的And

zyxNobita专栏 521

Android 那些你所不知道的Bitmap对象详解(转)

转载请注明本文出自xiaanming的博客(http://blog.youkuaiyun.com/xiaanming/article/details/41084843),请尊重他人的辛勤劳动成果,谢谢! 我们知道Android系统分配给每个应用程序的内存是有限的,Bitmap作为消耗内存大户,我们对Bitmap的管理稍有不当就可能引发OutOfMemoryError,而Bitmap对象在不同的And

kurtash的专栏 452

Android Bitmap图像优化

在Android应用开发中不可避免的会用到图形图像,这样就会生成Bitmap对象。如果在开发过程中没有处理好Bitmap对象就很容易产生Out Of Memory(OOM)的异常。以下列举几点使用Bitmap对象需要注意的地方:     一个Android应用程序最多只能使用16M的内存,在Android的 Android Compatibility Definition Document (C

专注Android开发 778

MC68HC908JB16:经典8位USB MCU架构解析与嵌入式开发实践

在嵌入式系统设计中,8位微控制器(MCU)因其极致的性价比、低功耗特性及成熟的生态,在成本敏感型应用中始终占据重要地位。其核心在于通过精简指令集与高效外设集成,实现对特定任务的精准控制。从技术原理看,这类MCU通常采用哈佛或冯·诺依曼架构,通过中断驱动和直接内存访问等机制协调外设工作,在实时性要求不苛刻的场景中表现出色。其技术价值体现在以极低的硬件资源实现可靠功能,大幅降低系统整体成本与功耗。典型的应用场景包括人机接口设备(HID)、智能传感器、消费电子外设及简易工业控制器等。本文以飞思卡尔HC08家族的M

431

setBackgroundResource造成的OOM和setBackground引发的思考

1、应用中每个界面调用setBackgroundResource,多次切换回造成OOM,出现原因是setBackgroundResource内部调用了setBackground(Drawable drawable);而Drawable生成方法内部调用BitmapFactory.decodexxx方法解析成Bitmap,再通过new BitmapDrawable(xxx)方式生成了Drawable。

u010886101的专栏 2364

Android开发之图片详解(3)

在Android中,Bitmap普遍是造成OOM的罪魁祸首,而且普遍都认为bitmap所占用的内存远大于Drawable,而且网上也提供了很多内存回收的方法以及建议,比如在activity销毁后主动去调用bitmap.recyle()方法等,那么到底是不是真的呢?我专门针对bitmap和drawble做了以下测试: 为了方便测出OOM,我专门将一张比较大的图片1270*1920放在了mdpi的文件

feiyang877647044的博客 1036

Bitmap优化和部分工具

2019独角兽企业重金招聘Python工程师标准>>> ...

weixin_34167043的博客 88

Android 图片处理以及recycle机制

我们经常会涉及到对相机拍照,然后处理拍照后的图片,最后在显示到UI上。如果处理的不好,就会导致系统卡顿,甚至会出现OOM,程序崩溃。 图片的处理public static BitmapDrawable getScaledDrawable(Activity a, String path) { if (a == null) return null; Display display = a.get

有酒平步上青天 2251
上一篇: 运用BitmapFactory.Options来改善程序加载图片效率和避免内存溢出
下一篇: 静态内部类和普通内部类的区别
恶魔果实
博客等级 码龄15年 6粉丝 13原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值