Preface
There are many performance optimization schemes, but not many can be applied to the project. When I
learned about layout optimization some time ago, I summarized many layout optimization schemes, but in the end they couldn t be applied to the project: [From entry to abandonment] android Layout optimization in-depth analysis
Today, as always, do not do the title party, I will introduce some practical startup optimization solutions to everyone~
for
This article mainly includes the following
1. What are the optimization directions for startup optimization?
2. How to accurately measure the startup time?
3. What are the practical optimization methods?
What are the optimization directions for startup optimization?
The application has three startup states, each of which affects the time required for the application to be displayed to the user: cold startup, warm startup, or hot startup. In a cold start, the application starts from the beginning. In the other two states, the system needs to bring applications running in the background to the foreground.
The start optimization mentioned in this article refers to cold start optimization
To optimize applications for fast startup, it is helpful to understand the system and application levels and how they interact in each state.
Cold start
Cold start means that the application starts from the beginning: the system process creates the application process after the cold start.
A cold start occurs when the application is started for the first time since the device is started or the system terminates the application.
This kind of startup brings the biggest challenge to minimizing the startup time, because the system and applications have more work to do than in the other two startup states.
At the beginning of the cold start, the system has three tasks, they are:
1. Load and start the application.
2. The blank startup window of the application is displayed immediately after startup.
3. Create an application process.
Once the system creates an application process, the application process is responsible for the subsequent stages:
1. Create an application object.
2. Start the main thread.
3. Create the master
4. Fill the view.
5. Layout the screen.
6. Perform initial drawing.
Once the application process finishes drawing for the first time, the system process will replace the currently displayed background window and replace it with the main
As shown above,
generally
How to measure startup time?
The easiest way
By viewing
in
Command measurement
for i in `seq 1 10` do adb shell am force-stop com.xx.xx sleep 2 adb shell am start-activity -W -n package name/activity name | grep "TotalTime" | cut -d '' -f 2 done Copy code
Sometimes we need to count the cold start performance of the app, and the single result is often inaccurate, and it needs to be counted several times and then averaged.
As above, use the script to start the homepage 10 times
The command measurement method is easy to use offline and can test competing products,
but it cannot be brought online and the measurement time cannot be accurately controlled.
So we usually need to bury the points manually
Buried point measurement
The key point of buried point measurement is the appropriate start and end time.
We generally use
, there are many options for the start end time
IdleHandler
Under normal circumstances, when the main thread process is in an idle state, it can be considered that the cold start has been completed, which is a relatively good timing.
But there is a problem, if
onWindowFocusChanged
when
but
but
In our project, the callback time and the interface display time have very little difference. It can be used as an optional solution according to the actual situation.
onPrewDrawListener
As mentioned above, the correct time to calculate the start-up time is to wait for the actual data to be displayed, for example, when the first item of the list is displayed, the start-up time is calculated.
We can add to the first item of the list
However , this method is strongly related to the business code and is more intrusive. Readers can also use according to the actual situation
AOP measurement method is time consuming
our
this can be used.
If you want to learn more, please refer to the time-consuming method of using AOP measurement
Use of TraceView and SystraceView
TraceView
Through it we can find out
This function is
In addition, in addition to writing code to
# Start the specified Activity, and sample tracking at the same time, -P end profiler app when entering the idle state
adb shell am start -n com.xxx.android/com.xxx.android.app.ui.activity.MainActivity -P/data/local/tmp/xxx-startup.trace --sampling 1000
# Pull .trace current directory files to the machine
adb pull/data/local/tmp/xx-startup.trace.
Copy code
As shown above: -P parameter means
after the start, by
More about
TraceView uses Zhihu
Android client to start optimization-Retrofit Agent
Systrace
Even if sampling and tracking are used, the measured results and actual results must still have a large deviation, which can only be used as a reference.
and
So we can use another
run
python systrace.py -t 10 -o/Users/xxx/trace.html -a com.xx.xxx duplicated code
among them:
After entering this command, you can see the prompt to start tracking. see
Wait until the end of the run to turn on the output
In addition to the above, we can also pass
More about
systrace use
knowing Android client startup optimization-Retrofit agent-Systrace
summary
1.
2.
3.
4.
Conventional optimization methods
1.Theme switch
start optimization. Start
Advantages
1. Simple to use.
2. Avoid starting the white screen and clicking the start icon does not respond.
Disadvantages
Treat the symptoms but not the root cause, but on the surface it produces a sense of quickness.
2. Asynchronous solution
We usually
The time-consuming initialization tasks are usually not small, so an optimization idea is parallel initialization.
This changes the initialization time from addition to seeking the maximum value.
Core idea: sub-threads share the tasks of the main thread, reducing time in parallel
Problems with conventional asynchronous solutions
1. The code is not elegant enough.
If we have 100 initialization tasks, then we need to submit 100 tasks.
2. Cannot be restricted to
some initialization tasks required third-party libraries in
3. Unable to realize the existence of dependencies.
Some initialization tasks have dependencies, for example, Jiguang Push requires equipment
Asynchronous starter scheme
The above introduces several problems of conventional asynchronous solutions. We can solve them through the
launcher. The core idea of the launcher is to make full use of multi-core
1. The first step is that we want to taskize the code. Taskization is an abbreviation, such as abstracting the startup logic into a task.
2. The second step is to generate a directed acyclic graph based on the sorting of dependencies of all tasks. This graph is automatically generated, that is, all tasks are sorted.
For example, we have a task
3. The third step is to execute multiple threads in sequence according to the sorted priority. For example, we now have three tasks
The general process of the launcher is shown above. We will introduce several open source launcher solutions for readers' reference.
JetPack App Startup
1.
2. Developers can use this component to streamline the startup sequence and explicitly set the order of initialization.
3. We do not need to define a separate for each component
This can greatly reduce the startup time of high applications, but
Its purpose is to manage the use of third-party libraries.
does not support asynchronous and asynchronous task management, so it does not meet our requirements.
Ali-alpha
AlphaIs based onPERTGraph constructionAndroidAsynchronous start framework, it is simple, efficient and fully functional. When the application starts, we usually have a lot of work to do. In order to improve the startup speed, we will try our best to make these work concurrently. However, there may be a dependency between these tasks, so we need to find a way to ensure the correctness of their execution order.AlphaIt s designed for this, users only need to define their owntaskAnd describe what it depends ontask, Add it toProjectin. The framework will automatically execute these concurrently and orderlytask, And throw out the results of the execution. due toAndroidThe application supports multiple processes, soAlphaSupports configuring different startup modes for different processes.
AnchorTask
AnchorTask is similar to Alpha
1. Supports concurrent execution of multiple tasks
2. Supports inter-task dependency and topological sorting
3. Supports task monitoring and time-consuming statistics
4. Supports designated task priority
5. Supports specifying whether to run in the main thread and whether to wait
The main point is
AnchorTask by programmer Xu Gong
Simple use is as follows, flexible configuration tasks and dependencies can be invoked through chain:
val project = AnchorProject.Builder().setContext(context).setLogLevel(LogUtils.LogLevel.DEBUG)
.setAnchorTaskCreator(ApplicationAnchorTaskCreator())
.addTask(TASK_NAME_ZERO)
.addTask(TASK_NAME_ONE)
.addTask(TASK_NAME_TWO)
.addTask(TASK_NAME_THREE).afterTask(
TASK_NAME_ZERO,
TASK_NAME_ONE
)
.addTask(TASK_NAME_FOUR).afterTask(
TASK_NAME_ONE,
TASK_NAME_TWO
)
.addTask(TASK_NAME_FIVE).afterTask(
TASK_NAME_THREE,
TASK_NAME_FOUR
)
.setThreadPoolExecutor(TaskExecutorManager.instance.cpuThreadPoolExecutor)
.build()
project.start().await()
Copy code
Delayed initialization scheme
Conventional plan
Some tasks we need to delay loading, the conventional method is through
Problems with conventional solutions
This method has the following problems:
1. The timing is inconvenient to control, and a suitable delay time cannot be determined
. 2. The code is not elegant enough and the maintenance cost is high. If there are multiple tasks, it needs to be added multiple times
. 3. It may cause the main thread to freeze. If the task is executed after 200 milliseconds is delayed, and the user is still sliding the list after 200, it will still be stuck.
Better solution
Core idea: Initialize and utilize delayed tasks in batches
so return after the task is all completed
public class DelayInitDispatcher {
private Queue<Task> mDelayTasks = new LinkedList<>();
private MessageQueue.IdleHandler mIdleHandler = new MessageQueue.IdleHandler() {
@Override
public boolean queueIdle () {
if (mDelayTasks.size()> 0 ){
Task task = mDelayTasks.poll();
new DispatchRunnable(task).run();
}
return !mDelayTasks.isEmpty();
}
};
public DelayInitDispatcher addTask (Task task) {
mDelayTasks.add(task);
return this ;
}
public void start () {
Looper.myQueue().addIdleHandler(mIdleHandler);
}
}
//Call
DelayInitDispatcher delayInitDispatcher = new DelayInitDispatcher();
delayInitDispatcher.addTask( new DelayInitTaskA())
.addTask( new DelayInitTaskB())
.start();
Copy code
Extremely lazy loading and early loading
Home page extremely lazy loading
Our homepage usually has multiple
we often use
This has a certain effect, but
more extreme lazy loading scheme is as follows:
1. When the first screen loads, only go to
2.
3. When occupying
With this scheme, it can be done at startup, only
if it is visible. If your
Layout preload
The official provides a class that can be used for asynchronous
1. Must be on site every time
2. Asynchronous loading
3. If in
Due to the above problems, one way of thinking is, can it be in the child thread in advance
core idea is as follows:
1. In the sub-thread during initialization
2.
3. Didn't get it
4. If it has not started
The advantages of this scheme:
can greatly reduce
Disadvantage
1. Due to
2.
Generally speaking, the advantages and disadvantages are obvious. Readers can follow the actual situation (mainly in the project).
specific implementation, please refer to: Magical pre-loading (pre-loading View, not data)
summary
This article mainly summarizes the direction of startup optimization and the method of accurately measuring startup time. It
focuses on several practical startup optimization solutions:
1. Asynchronous starter speeds up initialization
2. Lazy loader reduces stalls and makes code more elegant
3. The home page is extremely lazy to load, reducing the home page
4. The layout pre-loading scheme is greatly reduced
These programs are relatively practical, readers can try to apply in the project to see how much improvement ~
Reference
Application startup time
Several quick ways to obtain android interface performance data
[Performance optimization] Android cold start optimization
knows Android client startup optimization-Retrofit agent
explores Android startup optimization methods In-
depth exploration of Android startup speed optimization (on)