内存优化:内存泄漏排查、LeakCanary、大图优化、Bitmap 复用、OOM 治理;
1、什么是内存泄漏?
答案
程序已不再使用的对象,被强引用一直持有,GC 无法回收,长期堆积导致内存占用越来越高,引发卡顿、OOM。
2、Android 常见内存泄漏场景有哪些?
答案
- 静态变量持有 Activity / Fragment / View
- 匿名内部类、Handler 隐式持有页面引用
- 延时消息、Runnable 未取消,页面销毁还在排队
- 单例持有页面上下文
- 集合容器长期 add 对象不清理
- 资源未释放:广播、注册监听、动画、相机、文件流未关闭
- 非静态内部类持有外部类引用
3、内存泄漏怎么排查?有哪些工具?
答案
-
工具:LeakCanary、Android Studio Profiler、MAT
-
步骤:
- 用 Profiler 观察内存抖动、内存持续上涨不回落
- 抓取 Heap 堆文件,用 MAT 分析引用链
- 找出谁强引用了本该销毁的 Activity,定位泄漏源头
4、LeakCanary 原理和作用
答案
作用:自动检测内存泄漏、自动 dump 堆、分析引用链、给出泄漏原因。
原理:页面销毁后,延时主动触发 GC,观察对象是否仍被引用无法回收;如果回收不了,判定为泄漏,自动分析引用路径展示给开发者。
5、Handler 内存泄漏原因及解决
答案
原因:匿名 Handler / 延时消息隐式持有 Activity,页面 finish 后消息还在队列,强引用导致 GC 无法回收。解决:
- 用静态内部类 + 弱引用持有页面
- onDestroy 调用
removeCallbacksAndMessages(null)清空所有消息
6、Bitmap 为什么容易造成 OOM?
答案
Bitmap 像素数据占用内存极大;一张高清图内存可达几 MB 甚至几十 MB;大量加载大图、不解码压缩、不复用内存,极易堆内存溢出 OOM。
7、大图优化有哪些手段?
答案
- 图片按需压缩采样 inSampleSize 降低宽高像素
- 使用 WebP 格式减小体积
- 避免一次性加载超多高清大图
- 图片做缓存:内存缓存 + 磁盘缓存
- 不用的图片及时置空回收
8、Bitmap 复用原理(面试常问)
答案
利用 Bitmap 内存复用,复用已释放的 Bitmap 内存块,新建图片直接复用这块内存,不重新申请内存;减少内存分配与 GC,防止内存抖动和 OOM;
常用:BitmapFactory.Options 设置 inBitmap 实现复用。
9、什么是内存抖动?怎么产生?怎么优化?
答案
频繁快速创建、销毁大量临时对象,导致 GC 频繁频繁触发,造成 UI 卡顿。
优化:减少循环内 new 对象、复用对象、减少短时大对象创建。
10、OOM 常见原因及治理方案
答案
常见原因:
- 内存泄漏堆积
- 无节制加载大图、Bitmap 不压缩不复用
- 列表大量创建对象不回收
- 静态集合无限存数据不清理治理:排查并修复所有内存泄漏;大图采样压缩、Bitmap 复用;列表复用 ViewHolder;及时清空集合、释放资源;图片三级缓存管控。
11、Context 内存泄漏注意点
答案
工具类、单例尽量用 Application Context;
不要长期持有 Activity Context,避免页面无法回收。