从Andorid应用性能调优的角度看,应用启动类型一般分为冷启动、热启动和温启动。应用冷启动的耗时较长,因此主流手机厂商为了提升应用启动速度,一般会做一些优化方案,比如通过AI+应用预加载的方式,提前拉起应用进程,AOT编译提前将dex文件编译为字节码,省去解析过程等等。
下面简要介绍下应用冷启动和热启动:
冷启动
冷启动的基本过程:
系统层:
1、加载并启动应用。
2、启动后加载启动动画(一般是桌面应用或者框架层来实现)。
3、创建应用进程。
应用进程:
1、应用进程被Zygote创建后,将会创建应用的对象。
2、启动主线程(一般指ActivityThread)。
3、创建并启动Main Activity。
4、创建窗口和视图。
5、绘制布局。
6、执行窗口绘制。
下面通过trace来看下某个应用的冷启动过程。
热启动
热启动比较简单,启动时系统直接把应用栈顶的Activity放到前台。如果应用的所有activity还存在内存中,那么就可以避免重复的对象初始化、渲染和绘制操作。但如果系统内存不足时,应用进程的对象被回收,那这时热启动需要重新实例化对象,此时跟冷启动将界面显示到手机屏幕一样。
下面通过trace来看下某个应用的热启动过程。
由于应用进程已经存在,所以从trace里面看到热启动并没有bindApp的动作。
如何看应用启动时间
方法一:通过am start命令查看
adb shell am start -W com.android.settings/com.android.settings.Settings
输出:
Starting: Intent{act=android.intent.action.MAIN cat=[android.intent.category.LAUNCHER] cmp=com.android.settings/.Settings}
Staus:ok
LaunchState:COLD
Activity:com.android.settings/.Settings
TotalTime:354
WaitTime:355
Complete
方法二:通过systrace判断启动时间:从点击事件到绘制第一帧doframe;
排查应用启动慢的系统因素
- 排查测试机器与对比机器的配置是否一致
- 排查测试机器与对比机器的测试环境是否一致(网络、电池大小等)
- 排查测试app的版本是否一致;
- 排查cpu提频是否一致;
- 排查IO读写速度与对比机是否有较大的差异;
- 排查GPU频率是否一致;
- 排查app启动动画的形式是否有差异(桌面做动画还是框架)
- 排查app启动时自身是否有做大量的JIT优化操作,如果有的话排除干扰,可以执行命令:adb shell cmd package compile -m everything -f PKG_name;
- 排查app启动GC是否严重;
- 查看doframe的耗时(如果这个地方耗时,多数是app自身设计的问题)
- 排查TP的响应时间是否有差异;