如果(a& b)花费的时间多于(a)if(b)?

时间:2015-03-13 13:24:41

标签: java c# native

我使用以下简单的逻辑来回答像这样的question

1:   if(a)        // 1 operation
2:   if (b)       // 1 operation

1:  if(a && b) // 1, 1(&&), 1 => 3 operations. 

所以,2个操作与3个,但在第一个例子中,编译器需要调用另一个指令来执行。

这个逻辑是真的吗? 它取决于编译器吗? 调用像;这样的空指令会花费编译器一些值得注意的时间吗?

This 也讨论了同样的问题,但没有考虑这个逻辑。 请帮助我们澄清这个问题。

3 个答案:

答案 0 :(得分:4)

有两种方法可以回答 这样的问题:

1。)查看IL代码(和/或)组装代码生成并计算执行此代码所需的CPU周期(提示:这不适合初学者)

2.。)构建一个小型测试程序,大量执行这两个变体,使用StopWatch()创建一个有意义且可读的定时输出,运行几次。

3。)推测您认为编译器的优化步骤能够做什么以及该软件将做什么,与其他人争论几个小时

答案 1 :(得分:2)

我假设编译器会为您的两种情况生成相同的字节代码。所以我用两个不同的源文件测试了它:

public class Test1 {    
  public static void main(String[] args) {
    if (args[0].equals("a"))
      if (args[1].equals("b"))
        System.out.println("Foo");
  }    
}

和...

public class Test2 {    
  public static void main(String[] args) {
    if (args[0].equals("a") && args[1].equals("b"))
      System.out.println("Foo");
  }    
}

javap -c Test1等检查字节代码,结果完全相同:

  public static void main(java.lang.String[]);
    Code:
       0: aload_0
       1: iconst_0
       2: aaload
       3: ldc           #2                  // String a
       5: invokevirtual #3                  // Method java/lang/String.equals:(Ljava/lang/Object;)Z
       8: ifeq          30
      11: aload_0
      12: iconst_1
      13: aaload
      14: ldc           #4                  // String b
      16: invokevirtual #3                  // Method java/lang/String.equals:(Ljava/lang/Object;)Z
      19: ifeq          30
      22: getstatic     #5                  // Field java/lang/System.out:Ljava/io/PrintStream;
      25: ldc           #6                  // String Foo
      27: invokevirtual #7                  // Method java/io/PrintStream.println:(Ljava/lang/String;)V
      30: return

因此,表现将是相同的。虽然我欢迎评论,如果有人能想到一个产生不同字节码的例子。

我的结果是使用Java 1.7中的Oracle javac。结果可能与其他编译器不同,尽管我怀疑他们不会成为这种情况。

答案 2 :(得分:-1)

有两种方法可以考虑你的问题:

  1. Java语言定义

    • 语言定义第二个示例将使用短路执行,这意味着if语句将包含任何代码的情况下,第二个示例可以执行得更快
  2. JVM优化

    • JVM运行时将删除死代码块,如果它可以证明他们没有任何副作用
相关问题