2017-01-14 13 views
1

说我有一个用于例如方法isEven验证特定值,的方法第二个方法调用例如从磁盘或用户)。但在那之后我还需要偶数值的方法使用此方法:JIT编译器的优化:</p> <pre><code>public static boolean isEven(int evenSize) { return evenSize % 2 == 0; } </code></pre> <p>我用这种方法来验证外部输入(:用相同的参数

public static String padToEven(int evenSize, String string) { 
    if (!isEven(evenSize)) { // <-- duplication of isEven method 
     throw new IllegalArgumentException("evenSize argument is not even"); 
    } 

    if (string.length() >= evenSize) { 
     return string; 
    } 

    StringBuilder sb = new StringBuilder(evenSize); 
    sb.append(string); 
    for (int i = string.length(); i < evenSize; i++) { 
     sb.append('x'); 
    } 
    return sb.toString(); 
} 

所以基本上我们提供已经验证参数的padToEven()和参数使用相同isEven功能验证。 JIT编译器(比如在Java的第8版中)能够找到第二个调用并优化它吗?

你可以假设检查不依赖于动态值(即,它是确定于所提供的参数值)。它也没有任何除返回值之外的副作用,例如日志记录。

+0

显然,对于'isEven'而言,这并不重要,但例如, 'isPrime'在操作上的差异可能是显着的,特别是在循环内使用时。 –

+0

有趣的问题!然而,我怀疑这是否可以在一般情况下安全地确定这种重用。 –

+0

@BoristheSpider是的,可能会非常棘手。对于JIT编译器(副作用,状态)和调用而言,很多未知数都可能被相当多的字节代码分隔开来。 –

回答

2

我不认为Java做任何间分析的。但是,该方法有一些内联机会。当你内嵌的一切,然后有

if (evenSize % 2 != 0) { 
    throw new IllegalArgumentException("evenSize argument is not even"); 
} 
... some code not changing evenSize 
if (evenSize % 2 != 0) { 
    throw new IllegalArgumentException("evenSize argument is not even"); 
} 

这是相当微不足道的优化。这种内联不是你可以依赖的,因为内联限制很快就达到了。

其他优化

OTOH,测试是非常容易的,可能被优化以

public static boolean isEven(int evenSize) { 
    return (evenSize & 1) == 0; 
} 

它采用了更快的操作。但这不是我想要的东西(因为周围有很多其他代码,所以你无法获得太多)。


我想,最好的优化是消除StringBuilder。什么???是的,严重的是,一个char[]会做:

char[] result = new char[evenSize]; 
for (int i = 0; i < string.length(); i++) { 
    result[i] = string.charAt(i); 
} 
for (int i = string.length(); i < evenSize; i++) { 
    result[i] = 'x'; 
} 
return new String(result); 

前一段时间,我做了一些测试显示,它应该是这样更快。最近的JIT可能会改变这一点。不是重要的部分:

什么样的优化在这里有意义?

根本没有。除非你

  • 真的需要提高性能
  • 配置文件,并找到罪魁祸首
  • 准备花相当长的一段时间基准和分析

只是没有做到这一点。幸运的是,JIT针对简洁的代码进行了优化。它不能改进你的算法和数据结构,所以你可以在真正需要时进行优化。微观优化远没有那么有意义。

你上面的代码很好,不要碰它。

+0

太好了,谢谢!请注意,'isEven'方法只是通用验证方法的一个例子。我问的唯一的事情就是那个方法调用的重复。所以一切以“OTOH”为主题。其余部分是关于代码的其他部分的一个有趣的讨论,这很好,但没有回答这个问题。所以基本上答案是:除非内联,否则不会进行优化。 –

+0

@MaartenBodewes我已经意识到写太多w.r.t.这个问题,但我做了,因为我认为,它可能是有用的。 ;) – maaartinus

+1

正如我通常也给我的加密相关答案的安全建议,我几乎不抱怨那:)我把答案分成3部分,而不是2,希望你不介意。 –

相关问题