简单探究Android平台下' if ' 语句条件判断耗时情况

2017年6月13日

前言

  前几日在改Bug时看到好多调试时用的日志语句都被一个日志开关控制着它的执行权。形如:

1 if(Constants.LOG_TAG){
2     Log.d(TAG, "Initialize finish! index:" + idx);
3 }

又为了方便日后遇到问题时的分析,还要加上很多类似的日志语句。这时突然很好奇“大量的”条件判断语句需要多消耗多少系统资源,以及不同的条件表达式占用系统资源的差异情况。为此,特意设计了一个简单的小实验,通过取多组不同环境下这几种情形的耗时均值作为考量依据。

 

设计实验

  对指定的条件语句进行一亿次的运算,计算运算前后的时间差作为结果。

  1. 一亿次循环运算空跑的耗时情况;
  2. if语句条件表达式为简单运算的情况的耗时情况;
  3. if语句条件表达式为局部boolean且值为true;
  4. if语句条件表达式为局部boolean且值为false;
  5. if语句条件表达式为局部final boolean且值为false;
  6. if语句条件表达式为全局boolean且值为false;
  7. if语句条件表达式为全局final boolean且值为false;
  8. if语句条件表达式为另一个类对象中的实例变量boolean且值为false;
  9. if语句条件表达式为另一个类对象中的静态变量boolean且值为true;
  10. if语句条件表达式为另一个类对象中的静态变量boolean且值为false;
  11. if语句条件表达式为另一个类对象中的静态final布尔变量且值为true;
  12. if语句条件表达式为另一个类对象中的静态final布尔变量且值为false;
  13. if语句条件表达式为静态final变量boolean且值为false;
  14. if语句条件表达式为静态变量boolean且值为false;

 

实验环境

  操作系统:Android 5.1

  设备系统:4K智能电视

  处理器:Hi3751v620

  内存:2GB

 

代码设计

MainActivity.java 主要代码

  1     private final String TAG = "chorm";
  2 
  3     private final int chorm = 100000000;// 1亿
  4     private boolean fieldBool;
  5     private final boolean fieldBool2 = false;
  6     private static boolean B3 = false;
  7     private final static boolean B4 = false;
  8 
  9     private long getTime() {
 10         return SystemClock.uptimeMillis();
 11     }
 12 
 13     public void click(View v) {
 14         int counter;
 15 
 16         Log.i(TAG, "- Prebuilt -");
 17         counter = chorm;
 18         long start = getTime();
 19         do {
 20             counter--;
 21         } while (counter > 0);
 22         long end = getTime();
 23 
 24         Log.i(TAG, " - Demo begin -");
 25         // 1. 一亿次循环运算空跑的耗时情况;
 26         counter = chorm;
 27         start = getTime();
 28         do {
 29             counter--;
 30         } while (counter > 0);
 31         end = getTime();
 32         Log.d(TAG, "1:Time spent:" + (end - start) + "ms");
 33 
 34         // 2. if语句条件表达式为简单运算的情况的耗时情况;
 35         counter = chorm;
 36         start = getTime();
 37         do {
 38             counter--;
 39             if ((9 + 17) == 8) {
 40 
 41             }
 42         } while (counter > 0);
 43         end = getTime();
 44         Log.d(TAG, "2:Time spent:" + (end - start) + "ms");
 45 
 46         // 3. if语句条件表达式为局部boolean且值为true;
 47         counter = chorm;
 48         boolean localBool = true;
 49         start = getTime();
 50         do {
 51             counter--;
 52             if (localBool) {
 53 
 54             }
 55         } while (counter > 0);
 56         end = getTime();
 57         Log.d(TAG, "3:Time spent:" + (end - start) + "ms");
 58 
 59         // 4. if语句条件表达式为局部boolean且值为false;
 60         counter = chorm;
 61         localBool = false;
 62         start = getTime();
 63         do {
 64             counter--;
 65             if (localBool) {
 66 
 67             }
 68         } while (counter > 0);
 69         end = getTime();
 70         Log.d(TAG, "4:Time spent:" + (end - start) + "ms");
 71 
 72         // 5. if语句条件表达式为局部final boolean且值为false;
 73         counter = chorm;
 74         final boolean localBool2 = false;
 75         start = getTime();
 76         do {
 77             counter--;
 78             if (localBool2) {
 79 
 80             }
 81         } while (counter > 0);
 82         end = getTime();
 83         Log.d(TAG, "5:Time spent:" + (end - start) + "ms");
 84 
 85         // 6. if语句条件表达式为全局boolean且值为false;
 86         counter = chorm;
 87         start = getTime();
 88         do {
 89             counter--;
 90             if (fieldBool) {
 91 
 92             }
 93         } while (counter > 0);
 94         end = getTime();
 95         Log.d(TAG, "6:Time spent:" + (end - start) + "ms");
 96 
 97         // 7. if语句条件表达式为全局final boolean且值为false;
 98         counter = chorm;
 99         start = getTime();
100         do {
101             counter--;
102             if (fieldBool2) {
103 
104             }
105         } while (counter > 0);
106         end = getTime();
107         Log.d(TAG, "7:Time spent:" + (end - start) + "ms");
108 
109         // 8. if语句条件表达式为另一个类对象中的实例变量boolean且值为false;
110         counter = chorm;
111         AnotherClass ac = new AnotherClass();
112         start = getTime();
113         do {
114             counter--;
115             if (ac.bool) {
116 
117             }
118         } while (counter > 0);
119         end = getTime();
120         Log.d(TAG, "8:Time spent:" + (end - start) + "ms");
121 
122         // 9. if语句条件表达式为另一个类对象中的静态变量boolean且值为true;
123         counter = chorm;
124         start = getTime();
125         do {
126             counter--;
127             if (AnotherClass.BOOL) {
128 
129             }
130         } while (counter > 0);
131         end = getTime();
132         Log.d(TAG, "9:Time spent:" + (end - start) + "ms");
133 
134         // 10. if语句条件表达式为另一个类对象中的静态变量boolean且值为false;
135         counter = chorm;
136         start = getTime();
137         do {
138             counter--;
139             if (AnotherClass.BOOL2) {
140 
141             }
142         } while (counter > 0);
143         end = getTime();
144         Log.d(TAG, "10:Time spent:" + (end - start) + "ms");
145 
146         // 11. if语句条件表达式为另一个类对象中的静态final变量boolean且值为true;
147         counter = chorm;
148         start = getTime();
149         do {
150             counter--;
151             if (AnotherClass.BOOL3) {
152 
153             }
154         } while (counter > 0);
155         end = getTime();
156         Log.d(TAG, "11:Time spent:" + (end - start) + "ms");
157 
158         // 12. if语句条件表达式为另一个类对象中的静态final变量boolean且值为false;
159         counter = chorm;
160         start = getTime();
161         do {
162             counter--;
163             if (AnotherClass.BOOL4) {
164 
165             }
166         } while (counter > 0);
167         end = getTime();
168         Log.d(TAG, "12:Time spent:" + (end - start) + "ms");
169         
170         // 13. if语句条件表达式为静态final变量boolean且值为false;
171         counter = chorm;
172         start = getTime();
173         do {
174             counter--;
175             if (B4) {
176                 
177             }
178         } while (counter > 0);
179         end = getTime();
180         Log.d(TAG, "13:Time spent:" + (end - start) + "ms");
181         
182         // 14. if语句条件表达式为静态变量boolean且值为false;
183         counter = chorm;
184         start = getTime();
185         do {
186             counter--;
187             if (B3) {
188                 
189             }
190         } while (counter > 0);
191         end = getTime();
192         Log.d(TAG, "14:Time spent:" + (end - start) + "ms");
193 
194         Log.v(TAG, " - Demo end -");
195     }

 

AnotherClass.java

1 public class AnotherClass {
2     public static boolean BOOL = true;
3     public static boolean BOOL2 = false;
4     public static final boolean BOOL3 = true;
5     public static final boolean BOOL4 = false;
6     public boolean bool;
7 }

 

实验结果

  共进行了五个不同环境下的测试实验。

    第一组:开机后在首页

    第二组:打开了很多应用以后

    第三组:播放数字电视节目时启动测试应用。

    第四组:播放一段4K视频时启动测试应用。

    第五组:在首页启动测试应用。

    第六组:在首页启动测试应用。

                       单位:毫秒(ms)

序号 第一组 第二组 第三组 第四组 第五组 第六组 耗时均值  
1 347  344 348 346 344 344 345.5  
2 347  359  347  344  344 345  347.67  
3 346  348  346  345  344 344  345.5  
4 346  347  345  344  344 344  345  
5 347  346  346  344  344  345  345.17  
6 347  346  345  345  344  344  345.17  
7 346  346  346 344  344  344  345  
8 347  346  345  344  344  345  345.17  
9 2292  2277  2279  2268  2265  2264  2274.17  
10 1410 1411 1408 1411 1411 1411 1410.33  
11 345 345 344 345 344 344 344.5  
12 345 345 344 346 363 344 347.83  
13 346 345 350 345 345 345 346  
14 344 345 350 344 344 344 345.17  

 

结论

  • 对于if语句条件表达式的耗时应以条件结果为false的为准。
  • 大多数情况下条件判断所耗时间相当。
  • 当条件被判断为true时(对比3、4),即时后面的方法体是空的,也需要更多的时间来执行,对比9、10的结果更明显。
  • 非必须条件下不要在条件判断语句处作运算(结果2),尽可能地将运算过程放在编译时来执行。
  • 变量是否被final修饰似乎对结果没有什么影响(4、5与6、7),事实上这个结果让我也很迷惑。不排除是我的测试环境与测试方法的问题。
  • 变量定义在哪一个对象对结果没有什么影响(结果6、结果8 )
  • 对于另一个类对象中的静态变量,所花费的时间相较于其它情况长很多(结果9、结果10)。尽量不要使用其它类对象中的非final静态变量。

 

  我相信没什么应用的调试日志数量能达到1亿条或者更多。即使是1410.33毫秒,分成1亿份,它的时间也是微不足道的,并且市面上移动设备处理器通常都比我手里这块要好。因此,实际结论是:你想怎样用就怎样用。当然,日志打印的耗时情况就不在我们的讨论范围之内了。

posted @ 2017-06-13 11:00  大窟窿  阅读(3568)  评论(0编辑  收藏  举报