Java性能:true与Boolean.TRUE

Dim*_*ima 26 java performance boolean memory-footprint

哪个在性能和高效内存使用方面更好?

Boolean isItTrue(arg){ 
    return Boolean.TRUE;
}

boolean isItTrue(arg){
    return Boolean.TRUE
}

Boolean isItTrue(arg){
    return true;
}

boolean isItTrue(arg){
    return true;
}
Run Code Online (Sandbox Code Playgroud)

使用基本类型应该更快更容易,但另一方面,当使用对静态对象的引用时,不会创建新值.或者可能是它在编译器级别上进行了优化,true并且false被静态对象的引用所取代以节省内存?

Ste*_*n C 26

首先,使用任何一个优于其他优势的性能优势最有可能太小而无法相关.在绝大多数情况下,代码简单性/可读性/可维护性更为重要.


这些示例都不涉及创建Boolean实例.从理论上讲,4个中的3个将触发Boolean类的初始化......并且您的应用程序本来不会这样做.在这种极不可能的事件中,您的整个应用程序将分配2个原本无法分配的对象.


这个将等于或快于所有其他因为它只需要将寄存器设置为零.

boolean isItTrue(arg){
    return true;
}
Run Code Online (Sandbox Code Playgroud)

孤立地,这必须从存储器加载静态引用,而不是寄存器的零.但是,在某些情况下,JIT编译器可能能够优化它.

Boolean isItTrue(arg){ 
    return Boolean.TRUE;
}
Run Code Online (Sandbox Code Playgroud)

从表面上看,这涉及到Boolean.valueOf(true)对"box"的调用true,但是JIT编译器应该能够通过内联调用将其优化为与前一代码相同的代码.

Boolean isItTrue(arg){
    return true;
}
Run Code Online (Sandbox Code Playgroud)

从表面Boolean.booleanValue(Boolean.TRUE)上看,这涉及到"取消装箱"的呼吁Boolean.此调用可以内联.JIT编译器也可以避免加载Boolean对象的引用并获取其value字段.

boolean isItTrue(arg){
    return Boolean.TRUE
}
Run Code Online (Sandbox Code Playgroud)

最重要的是,4种替代方案的相对性能取决于JIT编译器在优化方面的成功程度.这取决于上下文,JIT编译器的具体情况,JVM设置等.在最好的情况下,JIT编译器(至少在理论上)可以为所有这些代码生成相同的(最佳)代码.


Jim*_*Jim 11

如果有任何性能提升,那么它就是无关紧要的.在任何情况下,Boolean.TRUE和Boolean.FALSE都不返回新对象.


djn*_*jna 9

有利于代码维护者对此类微优化的清晰度.问题不应该是"哪个更小/更快",首先表达你的意思.

如果该方法返回一个布尔对象,那么接收的任何人都需要确定它是否有可能为null,如果它 null则表示它可能意味着与true/false不同,例如"我们不知道".

所以返回布尔类型,如果这是你的意思,否则,如果你想允许Null,那么布尔.

如果返回一个布尔值

return true; // or false
Run Code Online (Sandbox Code Playgroud)

必须比依靠自动装箱更好,再次为了清晰和性能.

如果返回布尔值

return Boolean.TRUE
Run Code Online (Sandbox Code Playgroud)

必须是好的,它只是避免产生额外的垃圾,就像我反对微观优化一样,我认为没有任何价值在于故意效率低下.我认为你也明显地匹配了返回类型,这也更清楚了.


Tal*_*han 7

它们会快得多.我不认为这两者之间会有任何区别.

Boolean isItTrue(arg){ 
    return Boolean.TRUE;
}

boolean isItTrue(arg){
    return true;
}
Run Code Online (Sandbox Code Playgroud)

但是其他实现将会变慢,因为它将在后端进行装箱和拆箱,需要一段时间的处理器.


编辑

我通过实施4种不同的方式收集了一些事实.只是想与你分享,我不知道如果它的写方式那样做.

Boolean isItTrue(){ 
    return Boolean.TRUE;
}

Free Memory before start --> 16030936
Time taken in Secs --> 7.844
Free Memory After Process --> 15940472
Memory Usage --> 90464
Run Code Online (Sandbox Code Playgroud)
boolean isItTrue(){
    return Boolean.TRUE;
}

Free Memory before start --> 16030936
Time taken in Secs --> 10.109
Free Memory After Process --> 15940472
Memory Usage --> 90464
Run Code Online (Sandbox Code Playgroud)
Boolean isItTrue(){
    return true;
}

Free Memory before start --> 16030936
Time taken in Secs --> 7.906
Free Memory After Process --> 15940472
Memory Usage --> 90464
Run Code Online (Sandbox Code Playgroud)
boolean isItTrue(){
    return true;
}

Free Memory before start --> 16030936
Time taken in Secs --> 7.828
Free Memory After Process --> 15940472
Memory Usage --> 90464
Run Code Online (Sandbox Code Playgroud)

主类

public static void main(String[] args){
    NewClass n = new NewClass();

    long sysTime = System.currentTimeMillis();

    Runtime rt = Runtime.getRuntime();
    long freeMem = rt.freeMemory();
    System.out.println( "Free Memory before start --> " + freeMem );
    for( int i = 0; i < Integer.MAX_VALUE; i++ ){
        n.isItTrue();
    }
    System.out.println( "Time taken in Secs --> " + (System.currentTimeMillis() - sysTime)/1000D);
    System.out.println( "Free Memory After Process --> " + rt.freeMemory() );
    System.out.println( "Memory Usage --> " + ( freeMem - rt.freeMemory() ) );
}
Run Code Online (Sandbox Code Playgroud)

  • 众所周知,微型标记很难正确编写(因此通常的建议是描述您的实际应用程序).请查看http://www.ibm.com/developerworks/java/library/j-jtp02225/index.html和http://wikis.sun.com/display/HotSpotInternals/MicroBenchmarks (4认同)
  • 该基准测试存在可能导致结果无效的缺陷.即使数字有效,它们也不能代表方法的可能性,也不能代表JIT编译器优化它们的上下文.最后,对于2 ^ 31次调用,最佳到最差的增量为2.3秒= =在库存硬件上小于纳秒秒= 2或3个CPU时钟滴答.如果这具有代表性,那么它显然会降低到对典型应用程序性能影响最小的水平. (3认同)