关于ANR
-
什么是anr
- 应用程序无响应弹框
-
造成anr的原因
- 主线程做了耗时操作
-
android中那些操作是在主线程
- activity的所有生命周期回调都是执行在主线程
- Service默认是执行在主线程的
- BroadcaseReceiver的OnReceiver回调执行在主线程
- 没有使用子线程的Handler的handerMessage,post(Runnable)执行在主线程
- AsyncTask的回调中除了doInBackground,其他的都是执行在主线程
-
如何解决Anr
- 使用AsyncTask处理韩式IO操作
- 使用Thread或者HandlerThread提高优先级
- 使用handler来处理工作线程的耗时任务
- actiivty的onCreate和onResume回调中尽量避免耗时的代码
关于OOM
-
什么是OOM
- 当前占用的内存加上我们申请的内存资源超过了Dalvik虚拟机的最大内存限制就会抛出Out of memory异常
-
如何解决OOM
- 有关bitmap优化
- 图片显示(比如RecyclerView滑动,滑动时不加载图片)
- 图片压缩
- 计时释放bitmap.recycler()
- 使用Lru最近最少使用LruCache来存储对象put(key,value),使用的LinkHashmap
- 使用BitmapFactory。Options来计算inSampleSize(图片的缩略比)
- 三级缓存(内存、本地、网络)
- 有关bitmap优化
内存抖动
-
什么是内存抖动
- 内存抖动是指存在短时间内频繁地分配和回收,而频繁的gc会导致卡顿,严重时和内存泄漏一样会导致oom
-
内存抖动的原因
- 瞬间产生大量的对象会严重占用新生代的内存区域,当达到阈值,剩余控件不够的时候,就会触发GC,系统话费再GC上的时间越多,进行界面绘制或流音频处理的时间就越短。即使每次分配的对象占用了很少的内存,但是叠加在一起回增加heap的压力,从而触发更多其他类型的GC.这个操作有可能会影响到帧率,并使得用户感知到性能问题。
内存泄漏
内存泄漏是指无用对象(不再使用的对象)持续占有内存或无用的内存得不到及时释放,从而造成的内存空间的浪费称为内存泄漏
-
内存泄漏原因:
-
静态变量
- 静态变量的生命周期和应用的生命周期一样长。如果静态变量持有某个Activity的context,则会引发对应的Activity无法释放,导致内存泄漏。如果持有安排偏离擦听得context就没有问题
- 常见:单列模式:内部实现是静态变量和方法
- 静态的View:view默认持有Actiivty的context
-
非静态内部类和匿名内部类
- 常见:Handler,AsyncTask,TimerTask等,一般在处理多线程任务的时候
- 非静态的内部类和匿名内部类都会隐式地持有其外部类的引用,静态的内部类不会持有外部类的引用
当使用Actiivty的context注册监听,不再需要监听的时候没有取消注册
资源对象为关闭:BraodcastReceiver,ContentObserver,File,CUR搜人,Stream,Bitmap等资源,使用后未关闭会导致内存泄漏
-
UI卡顿
- 在UI线程中中轻微耗时操作,会导致UI线程卡顿
- 布局Layout过于复杂,无法再16ms内完成渲染
- 同一时间动画执行次数过多,导致CPU或GPU负载过重
- View过度绘制,导致某些像素再同一时间内被绘制多次,从而导致 CPU,GPU负载过重
- view频繁的触发mesure,layout,导致measure,layout累计耗时过多以及整个view频繁的重新渲染
- 内存频繁触发GC过多,导致展示阻塞渲染操作