越整理越要找更多资料,越写越发觉自己不懂的东西更多。学习的路还很长…
本文主要从 界面,内存,电量优化三个方面展开,梳理一下自己的知识。
界面、GPU
渲染性能
大多数用户感知到的卡顿等性能问题的最主要根源都是因为渲染性能。从设计师的角度,他们希望App能够有更多的动画,图片等时尚元素来实现流畅的用户体验。但是Android系统很有可能无法及时完成那些复杂的界面渲染操作。
Android系统每隔16ms发出VSYNC信号,触发对UI进行渲染,如果每次渲染都成功,这样就能够达到流畅的画面所需要的60fps,为了能够实现60fps,这意味着程序的大多数操作都必须在16ms内完成。
如果你的某个操作花费时间是24ms,系统在得到VSYNC信号的时候就无法进行正常渲染,这样就发生了丢帧现象。那么用户在32ms内看到的会是同一帧画面。
(fps:每秒传输帧数。人眼与大脑之间的协作无法感知超过60fps的画面更新。)
失帧原因:
用户容易在UI执行动画或者滑动ListView的时候感知到卡顿不流畅,是因为这里的操作相对复杂,容易发生丢帧的现象,从而感觉卡顿。有很多原因可以导致丢帧,也许是因为你的layout太过复杂,无法在16ms内完成渲染,有可能是因为你的UI上有层叠太多的绘制单元,还有可能是因为动画执行的次数过多。这些都会导致CPU或者GPU负载过重。
- layout太过复杂
- UI层级太深
优化方法:
布局优化:
- 删除布局中无用的控件和层级
- 选择性能较低的viewGroup(FrameLayout>LinearLayout>RelativeLayout)
- 巧用< merge/>标签
绘制优化:
- 移除Window默认的Background (getWindows().setBackgroudDrawable(null))
- 移除XML布局文件中非必需的Background
- 按需显示占位背景图片
- clipRect方法(绘制指定区域)<>
工具
- 开发者选项里面的 Show GPU view updates:查看视图更新的操作
- HierarchyViewer:查看布局,使得布局尽量扁平化,移除非必需的UI组件,这些操作能够减少Measure,Layout的计算时间。
内存、CPU
虽然Android有自动管理内存的机制,但是对内存的不恰当使用仍然容易引起严重的性能问题。
Android执行GC操作的时候,所有线程的任何操作都会需要暂停,等待GC操作完成之后,其他操作才能够继续运行。
通常来说,单个的GC并不会占用太多时间,但是大量不停的GC操作则会显著占用帧间隔时间(16ms)。如果在帧间隔时间里面做了过多的GC操作,那么自然其他类似计算,渲染等操作的可用时间就变得少了,并使得用户感知到性能问题(卡顿,数据被GC掉)。
导致GC频繁执行de原因:
- Memory Churn内存抖动,内存抖动是因为大量的对象被创建又在短时间内马上被释放。
造成内存不恰当使用的因素:
- (内存抖动)大量的对象被创建又在短时间内马上被释放导致频繁GC。
- (内存泄漏)不必要的数据不易被GC 导致内存占用过大,必要数据被优先清除。
- 使用占用内存大的对象
- 内存对象没有被重复利用
- …
工具:
为了寻找内存的性能问题,Android Studio提供了工具来帮助开发者。
- Memory Monitor:查看整个app所占用的内存,以及发生GC的时刻。(短时间内发生大量的GC操作是一个危险的信号。)
- Allocation Tracker:使用此工具来追踪内存的分配。
- Heap Tool:查看当前内存快照,便于对比分析哪些对象有可能是泄漏了的。
策略
- 减少对象占用的内存
- 内存de重复利用
- 避免对象的内存泄露
- 内存使用策略优化
电源
电量其实是目前手持设备最宝贵的资源之一,大多数设备都需要不断的充电来维持继续使用。
千万不能让你的应用成为消耗电量的大户。
有下面一些措施能够显著减少电量的消耗:
- 我们应该尽量减少唤醒屏幕的次数与持续的时间,使用WakeLock来处理唤醒的问题,能够正确执行唤醒操作并根据设定及时关闭操作进入睡眠状态。
- 某些非必须马上执行的操作,例如上传歌曲,图片处理等,可以等到设备处于充电状态或者电量充足的时候才进行。
- 触发网络请求的操作,每次都会保持无线信号持续一段时间,我们可以把零散的网络请求打包进行一次操作,避免过多的无线信号引起的电量消耗。关于网络请求引起无线信号的电量消耗,还可以参考这里:http://blog.csdn.net/sinat_15877283/article/details/50762297
献上我写这边博文的大纲: