《深入理解Java虚拟机》中讲语法糖时,提到了下面这个例子(不是原文中的例子,我自己改过):

public class AutoBoxingTest {

	/**
* @param args
*/
public static void main(String[] args) {
Integer a = 1;
Integer b = 2;
Integer c = 127;
Integer d = 127;
Integer e = 3;
Integer f = 3;
Long g = 3L;
System.out.println(c == d);
System.out.println(e == f);
System.out.println(e == (a + b));
System.out.println(e.equals(a + b));
System.out.println(g == (a + b));
System.out.println(g.equals(a + b));
}
}

输出结果:

true

true

true

true

true

false

使用JAD反编译后,结果:

import java.io.PrintStream;

public class AutoBoxingTest
{ public AutoBoxingTest()
{
// 0 0:aload_0
// 1 1:invokespecial #1 <Method void Object()>
// 2 4:return
} public static void main(String args[])
{
Integer integer = Integer.valueOf(1);
// 0 0:iconst_1
// 1 1:invokestatic #2 <Method Integer Integer.valueOf(int)>
// 2 4:astore_1
Integer integer1 = Integer.valueOf(2);
// 3 5:iconst_2
// 4 6:invokestatic #2 <Method Integer Integer.valueOf(int)>
// 5 9:astore_2
Integer integer2 = Integer.valueOf(127);
// 6 10:bipush 127
// 7 12:invokestatic #2 <Method Integer Integer.valueOf(int)>
// 8 15:astore_3
Integer integer3 = Integer.valueOf(127);
// 9 16:bipush 127
// 10 18:invokestatic #2 <Method Integer Integer.valueOf(int)>
// 11 21:astore 4
Integer integer4 = Integer.valueOf(3);
// 12 23:iconst_3
// 13 24:invokestatic #2 <Method Integer Integer.valueOf(int)>
// 14 27:astore 5
Integer integer5 = Integer.valueOf(3);
// 15 29:iconst_3
// 16 30:invokestatic #2 <Method Integer Integer.valueOf(int)>
// 17 33:astore 6
Long long1 = Long.valueOf(3L);
// 18 35:ldc2w #3 <Long 3L>
// 19 38:invokestatic #5 <Method Long Long.valueOf(long)>
// 20 41:astore 7
System.out.println(integer2 == integer3);
// 21 43:getstatic #6 <Field PrintStream System.out>
// 22 46:aload_3
// 23 47:aload 4
// 24 49:if_acmpne 56
// 25 52:iconst_1
// 26 53:goto 57
// 27 56:iconst_0
// 28 57:invokevirtual #7 <Method void PrintStream.println(boolean)>
System.out.println(integer4 == integer5);
// 29 60:getstatic #6 <Field PrintStream System.out>
// 30 63:aload 5
// 31 65:aload 6
// 32 67:if_acmpne 74
// 33 70:iconst_1
// 34 71:goto 75
// 35 74:iconst_0
// 36 75:invokevirtual #7 <Method void PrintStream.println(boolean)>
System.out.println(integer4.intValue() == integer.intValue() + integer1.intValue());
// 37 78:getstatic #6 <Field PrintStream System.out>
// 38 81:aload 5
// 39 83:invokevirtual #8 <Method int Integer.intValue()>
// 40 86:aload_1
// 41 87:invokevirtual #8 <Method int Integer.intValue()>
// 42 90:aload_2
// 43 91:invokevirtual #8 <Method int Integer.intValue()>
// 44 94:iadd
// 45 95:icmpne 102
// 46 98:iconst_1
// 47 99:goto 103
// 48 102:iconst_0
// 49 103:invokevirtual #7 <Method void PrintStream.println(boolean)>
System.out.println(integer4.equals(Integer.valueOf(integer.intValue() + integer1.intValue())));
// 50 106:getstatic #6 <Field PrintStream System.out>
// 51 109:aload 5
// 52 111:aload_1
// 53 112:invokevirtual #8 <Method int Integer.intValue()>
// 54 115:aload_2
// 55 116:invokevirtual #8 <Method int Integer.intValue()>
// 56 119:iadd
// 57 120:invokestatic #2 <Method Integer Integer.valueOf(int)>
// 58 123:invokevirtual #9 <Method boolean Integer.equals(Object)>
// 59 126:invokevirtual #7 <Method void PrintStream.println(boolean)>
System.out.println(long1.longValue() == (long)(integer.intValue() + integer1.intValue()));
// 60 129:getstatic #6 <Field PrintStream System.out>
// 61 132:aload 7
// 62 134:invokevirtual #10 <Method long Long.longValue()>
// 63 137:aload_1
// 64 138:invokevirtual #8 <Method int Integer.intValue()>
// 65 141:aload_2
// 66 142:invokevirtual #8 <Method int Integer.intValue()>
// 67 145:iadd
// 68 146:i2l
// 69 147:lcmp
// 70 148:ifne 155
// 71 151:iconst_1
// 72 152:goto 156
// 73 155:iconst_0
// 74 156:invokevirtual #7 <Method void PrintStream.println(boolean)>
System.out.println(long1.equals(Integer.valueOf(integer.intValue() + integer1.intValue())));
// 75 159:getstatic #6 <Field PrintStream System.out>
// 76 162:aload 7
// 77 164:aload_1
// 78 165:invokevirtual #8 <Method int Integer.intValue()>
// 79 168:aload_2
// 80 169:invokevirtual #8 <Method int Integer.intValue()>
// 81 172:iadd
// 82 173:invokestatic #2 <Method Integer Integer.valueOf(int)>
// 83 176:invokevirtual #11 <Method boolean Long.equals(Object)>
// 84 179:invokevirtual #7 <Method void PrintStream.println(boolean)>
// 85 182:return
}
}

从中可以看出,最后false产生的原因是Long类型和Integer进行比较,不同类型自然不会equal了。

另外,原文中使用的是321而不是127,这样做java的字节码中将使用sipush而不是bipush,此时==判断会变为false,目前我不太明白为啥会这样,望大神指点。

Java中自动装箱代码初探的更多相关文章

  1. java中自动装箱带来的性能问题

    之前没有特别注意自动封装所带来的性能问题,今天看了effective java,实验了一下,结果大吃一惊: 考虑下面这段代码: public static void main(String args[ ...

  2. Java中自动装箱与拆箱

    一.什么是封装类? Java中存在基础数据类型,但是在某些情况下,我们要对基础数据类型进行对象的操作,例如,集合中只能存在对象,而不能存在基础数据类型,于是便出现了包装器类.包装器类型就是对基本数据类 ...

  3. java中自动装箱的问题

    package wrapper; public class WrapperDemo { public static void main(String[] args) { Integer a=new I ...

  4. 深入剖析Java中的装箱和拆箱

    深入剖析Java中的装箱和拆箱 自动装箱和拆箱问题是Java中一个老生常谈的问题了,今天我们就来一些看一下装箱和拆箱中的若干问题.本文先讲述装箱和拆箱最基本的东西,再来看一下面试笔试中经常遇到的与装箱 ...

  5. 从别人那淘的知识 深入剖析Java中的装箱和拆箱

    (转载的海子的博文   海子:http://www.cnblogs.com/dolphin0520/) 深入剖析Java中的装箱和拆箱 自动装箱和拆箱问题是Java中一个老生常谈的问题了,今天我们就来 ...

  6. 第六节:详细讲解Java中的装箱与拆箱及其字符串

    前言 大家好,给大家带来详细讲解Java中的装箱与拆箱及其字符串的概述,希望你们喜欢 装箱与拆箱 封装类有:Byte , short , Integer , Character , long , Fl ...

  7. [ 转载 ]学习笔记-深入剖析Java中的装箱和拆箱

    深入剖析Java中的装箱和拆箱 自动装箱和拆箱问题是Java中一个老生常谈的问题了,今天我们就来一些看一下装箱和拆箱中的若干问题.本文先讲述装箱和拆箱最基本的东西,再来看一下面试笔试中经常遇到的与装箱 ...

  8. 【转】深入剖析Java中的装箱和拆箱

    深入剖析Java中的装箱和拆箱 自动装箱和拆箱问题是Java中一个老生常谈的问题了,今天我们就来一些看一下装箱和拆箱中的若干问题.本文先讲述装箱和拆箱最基本的东西,再来看一下面试笔试中经常遇到的与装箱 ...

  9. Java的自动装箱/拆箱

    概述 自JDK1.5开始, 引入了自动装箱/拆箱这一语法糖, 它使程序员的代码变得更加简洁, 不再需要进行显式转换.基本类型与包装类型在某些操作符的作用下, 包装类型调用valueOf()方法将原始类 ...

随机推荐

  1. Android框架之路——GreenDao3.2.2的使用

    一.简介 GreenDAO是一个开源的安卓ORM框架,能够使SQLite数据库的开发再次变得有趣.它减轻开发人员处理低级数据库需求,同时节省开发时间. SQLite是一个令人敬畏的内嵌的关系数据库,编 ...

  2. NAT(网络地址转换)协议

    NAT(Network Address Translator)是网络地址转换,它实现内网的IP地址与公网的地址之间的相互转换,将大量的内网IP地址转换为一个或少量的公网IP地址,减少对公网IP地址的占 ...

  3. StringUtil方法全集

    org.apache.commons.lang.StringUtils中方法的操作对象是Java.lang.String类型的对象,是JDK提供的String类型操作方法的补充,并且是null安全的( ...

  4. bt种子文件是什么(包括bt文件结构)

    bt种子文件是什么(包括bt文件结构) 一.总结 一句话总结:带特定格式特定信息(资源的url相关信息)的一个字符串(和json有点异曲同工之妙的感觉). 1.bt种子文件和json的区别和联系? 共 ...

  5. 浅谈如何优化SQL Server服务器

      在中国,使用SQLServer数据库的用户和企业是最多的,那么如何去设计和优化SQLSerer服务器呢,DBA应该遵循那些准则和方法呢,下面就将我的经验与大家分享,希望对大家有所帮助. AD:   ...

  6. WebUI 常用

    //鼠标移动显示div //position:absolute这个是绝对定位:是相对于浏览器的定位.比如:position:absolute:left:20px;top:80px; 这个容器始终位于距 ...

  7. let和const命令新总结

    let声明变量 新特性 声明的变量仅仅在块级作用域有效 块级作用域:外层作用于无法读取内层作用于周中的变量,内层作用域可以定义外层作用于中的同名变量 不存在变量提升 暂时性死区 只要在块级作用域内存在 ...

  8. python中的单引号双引号和三引号

    python的单引号和双引号没有本质的区别,而三引号有两种作用:注释和换行 一. 单引号中可以包含双引号,双引号中可以包含单引号 print("好好学习,'天天向上'") 结果: ...

  9. Handsontable 的数据保存(增删改查+导出excel)

    项目用到handsontable 插件 根据官网 API写的handsontable初始化, 数据展示, ajax请求, 参数封装, Controller参数接受 全局容器 var AllData = ...

  10. SpringBoot邮件发送功能

    快速入门 在Spring Boot的工程中的pom.xml中引入spring-boot-starter-mail依赖: <dependency> <groupId>org.sp ...