1、启动优化
1.1、启动类型
冷启动流程:用户点击 -> IPC -> Process.start创建进程 -> ActivityThread(单独进程的入口) -> bindApplication(创建Application) -> LifeCycle(Activity) -> ViewRootImpl界面绘制
冷启动之前会进行的操作:启动App,加载空白Window,创建进程。随后会创建Application,启动主线程,创建Activity,加载布局,布置屏幕,首帧绘制。主要对Application和Activity生命周期进行优化。
热启动:后台切换到前台。
温启动:只会重走Activity的生命周期。
1.2、启动时间
1、adb方式:
adb shell am start -W 包名/包名.首屏Activity
ThisTime:最后一个Activity启动耗时
TotalTime:所有Activity启动耗时
WaitTime:AMS启动Activity的总耗时
2、手动打点方式:启动时埋点,可以线上使用
开始时间Application
@Override
protected void attachBaseContext(Context base) {
super.attachBaseContext(base);
//开始计时
}
结束计时
//Activity中
@Override
public void onWindowFocusChanged(boolean hasFocus) {
super.onWindowFocusChanged(hasFocus);
//结束计时
}
//或者Adapter
@Override
public void onBindViewHolder(@NonNull final ViewHolder holder, int position) {
if (position == 0 && !mHasRecorded) {
mHasRecorded = true;
holder.layout.getViewTreeObserver()
.addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() {
@Override
public boolean onPreDraw() {
//结束计时
return true;
}
});
}
}
1.3、工具
traceview:图形展示执行时间、调用栈;包含所有线程。缺点:运行变慢。
android.os.Debug.startMethodTracing();//也可以调用startMethodTracing(String traceName) 设置trace文件的文件名
android.os.Debug.stopMethodTracing();//放在结束调试的地方
生成文件在:Android/data/包名/files
systrace:结合Android内核的数据,生成Html报告。轻量级,开销小。直接反应cpu利用率。
//b:大小,t:时间,o:生成文件名字
python systrace.py -b 32768 -t 5 -a 包名 -o html文件 sched gfx view wm am app
//项目代码
TraceCompat.beginSection(mTask.getClass().getSimpleName());
TraceCompat.endSection();
cputime代码消耗cpu的时间(重要指标);walltime:代码执行时间。
1.4、统计方法消耗时间
AOP:针对同一类问题统一处理。
AspectJ
https://github.com/HujiangTechnology/gradle_plugin_android_aspectjx
classpath 'com.hujiang.aspectjx:gradle-android-plugin-aspectjx:2.0.0'
apply plugin: 'android-aspectjx'
implementation 'org.aspectj:aspectjrt:1.8.+'
例如PerformanceAop类
1.4、Theme小技巧
Theme切换:感觉上更快。
drawable下创建.xml
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" android:opacity="opaque">
<!-- The background color, preferably the same as your normal theme -->
<item android:drawable="@android:color/white"/>
<!-- Your product logo - 144dp color version of your app icon -->
<item>
<bitmap
android:src="@mipmap/splash"
android:gravity="fill"/>
</item>
</layer-list>
styles中设置
<item name="android:windowBackground">@drawable/lanucher</item>
首屏Activity引用
android:theme="@style/Theme.Splash"
Activity中
setTheme(R.style.AppTheme);
//super.onCreate之前切换真正的style
super.onCreate(savedInstanceState);
1.5、异步解决方案-启动器
异步优化:子线程分担主线程任务。
Application中的sdk初始化如果不需要再主线程中执行,那么就异步执行。CountDownLatch。
线程池创建线程数,根据手机cup
private static final int CPU_COUNT = Runtime.getRuntime().availableProcessors();
private static final int CORE_POOL_SIZE = Math.max(2, Math.min(CPU_COUNT - 1, 4));
启动器:充分利用cpu多核,自动梳理任务顺序
代码Task化,启动逻辑抽象为Task。根据任务依赖关系排序生成一个有向无环图。多线程按照排序后的优先级依次执行。
工具类:TaskDispatcher,例子:主线程Task:InitWeexTask;子线程Task:InitAMapTask;等待Task:InitJPushTask。
延迟初始化:在MainActivity的onFeedShow方法中调用DelayInitDispatcher利用addIdleHandler