繁体   English   中英

编译器为自动装箱生成了什么代码?

[英]What code does the compiler generate for autoboxing?

当Java编译器将一个原语自动装箱到包装器类时,它会在幕后生成什么代码? 我想它叫:

  • 包装器上的valueOf()方法
  • 包装器的构造函数
  • 其他一些魔术?

您可以使用javap工具自己查看。 编译以下代码:

public class AutoboxingTest
{
    public static void main(String []args)
    {
        Integer a = 3;
        int b = a;
    }
}

编译和反汇编:

javac AutoboxingTest.java
javap -c AutoboxingTest

输出是:

Compiled from "AutoboxingTest.java"
public class AutoboxingTest extends java.lang.Object{
public AutoboxingTest();
  Code:
   0:   aload_0
   1:   invokespecial   #1; //Method java/lang/Object."<init>":()V
   4:   return

public static void main(java.lang.String[]);
  Code:
   0:   iconst_3
   1:   invokestatic    #2; //Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
   4:   astore_1
   5:   aload_1
   6:   invokevirtual   #3; //Method java/lang/Integer.intValue:()I
   9:   istore_2
   10:  return

}

因此,正如您所看到的,autoboxing调用静态方法Integer.valueOf() ,并且autounboxing在给定的Integer对象上调用intValue() 没有别的,真的 - 这只是语法糖。

我想出了一个单元测试,证明调用了Integer.valueOf()而不是包装器的构造函数。

import static org.junit.Assert.assertNotSame;
import static org.junit.Assert.assertSame;

import org.junit.Test;

public class Boxing {
    @Test
    public void boxing() {
        assertSame(5, 5);
        assertNotSame(1000, 1000);
    }
}

如果您查找Integer#valueOf(int)的API文档,您将看到它已添加到JDK 1.5中。 所有包装器类型(尚未包含它们)都添加了类似的方法来支持自动装箱。 对于某些类型,还有一个额外的要求,如JLS中所述:

如果被装箱的值ptruefalse ,一个byte ,范围为\\char ,或者介于-128127之间的intshort ,则让r1r2为任意两个装箱转换的结果p 始终是r1 == r2的情况。 §5.1.7

值得注意的是, long s不受相同要求的限制,尽管-128..127范围内的Long值缓存在Sun的实现中,就像其他整数类型一样。

我还发现在我的Java编程语言副本中,它表示从\\ÿ char值被缓存,但当然每个规范的上限是\ (并且Sun JDK符合此规范中的规范)案件)。

我建议大量使用jad和反编译代码。 你可以学到很多关于java实际做的事情。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM