TraceView是什么,TraceView 是 Android 平台特有的数据采集和分析工具,主要用做热点分析,找出最需要优化的点。TraceView 从代码层面分析性能问题,针对每个方法来分析,比如当我们发现我们的应用出现卡顿的时候,我们可以来分析出现卡顿时在方法的调用上有没有很耗时的操作,通过TraceView,可以得到两种数据。
- 单次执行最耗时的方法
- 执行次数最多的方法
要打开上面的面板,一般有两种方式:
1、第一种方式:
首先选择跟踪范围,在想要根据的代码片段之间使用以下两句代码:
Debug.startMethodTracing(“/sdcard/test.trace”);
Debug.stopMethodTracing();
然后启动Android Device Monitor-->File-->openFile,打开traceview文件即可。
2、第二种方式,同样是要先打开Android Device Monitor:
先选择应用进程,然后点击Start Method Profiling(开启方法分析),按钮会变为Stop Method Profiling(停止方法分析),开启方法分析后,对应用的目标页面进行测试操作,测试完毕后停止方法分析,界面会自动跳转到 DDMS 的 trace 分析界面。
两种方式的对比:第一种方式更精确到方法,起点和终点都是自己定,不方便的地方是自己需要添加方法并且要导出文件,第二种方式的优缺点刚好相反。
3、分析方式:
下面写一个DEMO,来分别模拟调用次数不多,但每次调用却需要花费很长时间的函数,和自身占用时间不长,但调用却非常频繁的函数。
public class MainActivity extends Activity { int count = 0; long longCount=-1; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); Debug.startMethodTracing("hello"); //线程1 new Thread(new Runnable() { @Override public void run() { printNum(); } },"printNum_thread").start(); //线程2 new Thread(new Runnable() { @Override public void run() { calculate(); } },"calculate_thread").start(); } @Override protected void onDestroy() { super.onDestroy(); Debug.stopMethodTracing(); } private void printNum() { for (int i = 0; i < 20000; i++) { print(); } } /** * 模拟一个自身占用时间不长,但调用却非常频繁的函数 */ private void print(){ count=count++; } /** * 模拟一个调用次数不多,但每次调用却需要花费很长时间的函数 */ private void calculate(){ for (int i = 0; i < 1000; i++) { for (int j = 0; j < 1000; j++) { for (int l = 0; l < 1000; l++) { if(longCount>10){ longCount=-10; } } } } Log.e("MainActivity",String.valueOf(longCount)); } }
现在来分析一下采集的数据。先看线程面板
在线程面板上发现我们应用中的三个线程,main线程,这个线程是都会有的,还有printNum_thread,calculate_thread两个线程。
再看时间线面板:
展开后,大多数有以下两个类别:
- Parents:调用该方法的父类方法
- Children:该方法调用的子类方法
如果该方法含有递归调用,可能还会多出两个类别: - Parents while recursive:递归调用时所涉及的父类方法
- Children while recursive:递归调用时所涉及的子类方法
至于数据分析面板红色框中,各个字段的含义如下:
开发者最关心的数据有:
很重要的指标:Calls + Recur Calls / Total , 最重要的指标: Cpu Time / Call
因为我们最关心的有两点,一是调用次数不多,但每次调用却需要花费很长时间的函数。这个可以从Cpu Time / Call反映出来。另外一个是那些自身占用时间不长,但调用却非常频繁的函数。这个可以从**Calls + Recur Calls / Total **反映出来。
点击Calls + Recur Calls这一栏,可以按照方法调用次数排序,如下图,可以看出print方法执行了2000次。
点击Cpu Time / Call这一栏,可以按照方法调用时间排序,如下图,
可以看到calculate方法执行了13s多,非常的耗时。
这是模拟的两个极端的情况,实际情况下,分析的难度比较大,但是当体验卡顿的时候,我们可以借助TraceView来定位问题。所以TraceView虽说不常用,但是还是很有意义的!