Android内存优化

一、内存管理方式

1、


2、


3、



1)dumpsys meminfo +包名查看堆栈信息



MEMINFO in pid 5073 [com.android.mooc.hexter.memopti]

进程5073

包名:com.android.mooc.hexter.memopti

pss:物理内存的使用情况

Heap Size:堆的尺寸

Heap Alloc:堆分配了多少

Heap Free:堆富余了多少

Native Heap: JNI开发中的堆

Dalvik Heap:虚拟机的堆

Stack:堆栈的大小

Ashmem:共享内存的大小

.so mmap:   .so的内存使用

.apk mmap:  apk的内存使用



2)不用的内存、不用的垃圾由GC负责处理。GC只有在堆Heap的剩余空间不够时才发出垃圾回收,但是垃圾不会马上放到free heap空间里面,只有当下次回收时发现空间不够了,GC才会在自己的堆里面把垃圾全部都清理掉,释放给free的空间,如果此时剩余空间够了,则直接在剩余空间中进行分配。


4、


如果一个app把内存占光,则企业的app则无法运行



5、


②LRU算法:最近使用的排在最前面,最少可能的被清理掉

③内存变动时会毁掉onTrimMemory方法,会把系统内存的level打印出来,判断level值释放手机内存



二、APP内存优化方法

1、


2、




1)字符串通过+的方式进行字符串拼接,会产生中间字符串内存块,这些都是没有用的

2)字符串拼接和Stringbuilder方式拼接字符串耗时比较

给二维矩阵赋值



字符串拼接的代码



StringBuilder拼接代码



点击字符串拼接的按钮:刚开始拼接运行速度挺快的,都是毫秒级别,后来越来越慢,都是秒的级别



耗时大概8s左右



③点击StringBuilder拼接的按钮:几乎是瞬间完成,只用了3毫秒,比上一种方式快了不仅仅一点点





3、ArrayMap、SparseArray替换HashMap,调用方法是一样的,但是使用效率比HashMap高。一方面,内存使用更少,第二方法,如果数据比较多,这两个效率比较高


4、内存抖动是变量申请不当引起的。比如说突然申请了很多变量或多内存空间,但是很快不用了,但是又申请了很多内存。就是很快申请很多内存又很快不用,从monitor中可以看到锯齿一样的内存很快提高又很快下来,就是内存抖动。内存抖动时间过长就会影响app运行的流畅性。


代码:








优化:

将strMatrix变量放在外面,重复使用


5、


6、


7、内存泄漏





引起的原因:

内部类默认是引用activity的引用的,当tread中执行了耗时操作,activity退出后,线程仍然在运行,由于持有了外部类的引用,导致activity无法被gc回收,可以使用的堆越来越小。如果线程中没有执行耗时操作,是不会引起问题的,执行完就销毁,不会持有外部类的引用,gc就可以回收activity。解决办法就是将其放在service中




8、


三、OOM问题优化

1、


1)


变量的声明周期是和变量申请的声明周期一样的,在变量声明周期内,变量是不会被gc回收的。

软引用与强引用的声明周期是一样的,但是运行过程中可以被gc回收

2、

得到内存变化的通知



level的值





3、



4、

代码:










第一个按钮:获取并打印图片



第二个按钮进行优化后:根据屏幕的宽高只获取图片的宽高,进行压缩后进行显示







第三个按钮,直接修改RGB




第四个按钮:部分加载图片






5、软引用方式管理图片




单例模式



放图片的时候先清理缓存,因为有的软引用使用的图片已经被回收了,然后再放入数据





获取图片,如果存在,返回图片



清理缓存。系统回收软引用,遍历队列,如果不为空,从map中移除





清空所有数据





通过软引用管理多张图片,不好的地方就是回收图片是随机的,可能回收的图片下次还需要使用




6、内存缓存,使用了lru算法

linkhashmap专门用来管理lru算法,因为线程不安全,所以外面套了一个synchronizemap





获取相应的图片



存储图片,如果原来存在图片,需要更新。

减去原来的尺寸是因为要放入新的图片,放入新的图片,原来的图片就放弃掉了。放入新的图片时加上新图片的大小








判断是否大于最大限制,如果大于获取迭代器。从最近最少用的图片开始进行迭代,获取到相应的图片。减去其大小,实际上就是放弃掉了,然后remove掉。remove掉后说明最近很少用的图片就被释放掉了,释放掉后gc就会回收。如果释放后还大于最大限制,则不停地释放,直到满足条件为止。









注:

1、参考资料:https://www.imooc.com/video/13670

2、ps命令查看进程id和堆大小



5、健康内存的击中方法


②通过代码打印内存信息


③使用Android  Monitor监控




内存变换情况



Tools-->Android-->Android Device Monitor



点击获取GC数据




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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值