深入理解Java自动装箱拆箱机制
1、自动装箱与拆箱的定义
装箱就是自动将基本数据类型转换为包装器类型(int-->Integer);
拆箱就是自动将包装器类型转换为基本数据类型(Integer-->int)。
Java中的数据类型分为两类:一类是基本数据类型,另一类是引用数据类型。如下图:
基本类型 | 二进制位数 | 分装类 |
int | 32(4字节) | Integer |
byte | 8(1字节) | Byte |
long | 64(8字节) | Long |
short | 16(2字节) | Short |
float | 32(4字节) | Float |
double | 64(8字节) | Double |
char | 16(2字节) | Character |
boolean | 1(1/8字节) | Boolean |
由上可知Java中的基本数据类型有八种分别是:int(4字节) byte(1字节) short(2字节) long(8字节) float (4字节) double(8字节) char(2字节) boolean(1byte)基本数据类型不是对象,不能使用对象的方法。将基本数据类型转换为对象就是自动装箱的过程。下面是基本数据类型与封装器类之间对应的关系。
2、自动装箱
public static void main(String[] args) {
int a=3;
//定义一个基本数据类型的变量a赋值3
Integer b=a;
//b是Integer 类定义的对象,直接用int 类型的a赋值
System.out.println(b);
//打印结果为3
}
上面的代码中 Integer b=a; 一个对象怎么赋值成了基本数据类型的变量,其实这就是自动装箱的过程,上面程序在执行Integer b=a;的时候调用了Integer.valueOf ( int i ) 方法,Integer b=a; 这段代码等同于:Integer b=Integer.valueOf ( a ) 。下面是对 Integer.valueOf ( int i ) 方法简化后的源码:
public static Integer valueOf(int i) {
if (i >= -128 && i <= 127)
return IntegerCache.cache[i + 127];
//如果i的值大于-128小于127则返回一个缓冲区中已存在的一个Integer对象
return new Integer(i);
//否则返回 new 一个Integer 对象
}
可以看到Integer.valueOf ( a )其实是返回了一个Integer的对象。因此由于自动装箱的存在Integer b=a 这段代码是没有毛病的。其实更简化的来写可以这样:Integer b=3,同样这段代码等价于:Integer b=Integer.valueOf (3 ) 。
上面的这段代码中:IntegerCache.cache[i + 127],下面是简化后的源码:
private static class IntegerCache { static final Integer cache[];
//定义一个Integer类型的数组且数组不可变
static {
//利用静态代码块对数组进行初始化。
cache = new Integer[256];
int j = -128;
for(int k = 0; k < cache.length; k++)
cache[k] = new Integer(j++);
} //cache[]原来是一个Integer 类型的数组(也可以称为常量池),value 从-128到127,
public static Integer valueOf(int i) {
if (i >=-128 && i <= 127)
return IntegerCache.cache[i + (-IntegerCache.low)];
//如果装箱时值在-128到127之间,之间返回常量池中的已经初始化后的Integer对象。
return new Integer(i);
//否则返回一个新的对象。
}
}
从上面代码可知,IntegerCache 类在初始化的时候,生成了一个大小为 256 的integer 对象的常量池,并且integer.val 的值从-128-127之内,在自动装箱时候,基本数据类型在该范围内的,则直接从该缓存区获取对应的Ingeter对象并返回,超出该范围,则重新创建Ingeter对象并返回;
3、自动拆箱
public static void main(String[] args) {
Integer b=new Integer(3);
//b为Integer的对象
int a=b;
//a为一个int的基本数据类型
System.out.println(a);
//打印输出3。
}
当封装类自动拆箱时,其实 int a=b,自动调用了b.intValue()方法,这段代码等价于:int a=b.intValue(),来看看inValue()方法到底是什么,下面是源码:
//自动拆箱时调用的方法,并直接返回基本数据类型
public int intValue() {
return value;
}
private final int value;
//而自动装箱时,通过构造函数创建对应的封装类,并将该基本数据类型赋值给该类的静态成员变量
public Integer(int value) {
this.value = value;
}
4、相关题目
自动装箱和拆箱已经解决了,看看下面的代码输出什么:
public static void main(String[] args) {
//
Integer a=new Integer(123);
Integer b=new Integer(123);
System.out.println(a==b);//输出 false
//分别创建两个封装类对象,比较的对象的引用类型变量,则不相等 //2
Integer c=123;
Integer d=123;
System.out.println(c==d);//输出 true
//对于同一个值,且值在-128~127范围内,自动装箱时直接返回缓存区已存在的Ingeter对象,则他们的引用类型变量是相等的,c、f为指向同一个对象 //
Integer e=129;
Integer f=129;
System.out.println(e==f);//输出 false
//自动装箱时,值超过了-128~127范围内,重新创建Ingeter对象,则e、f为指向两个对象 //
int g=59;
Integer h=new Integer(59);
System.out.println(g==h);//输出 true
//当一个基本数据类型,跟封装类做对比时,封装类会自动拆箱成基本数据类型,然后再比较值得大小
}
原文:https://blog.csdn.net/MyArray/article/details/89381893
深入理解Java自动装箱拆箱机制的更多相关文章
- java自动装箱拆箱总结
对于java1.5引入的自动装箱拆箱,之前只是知道一点点,最近在看一篇博客时发现自己对自动装箱拆箱这个特性了解的太少了,所以今天研究了下这个特性.以下是结合测试代码进行的总结. 测试代码: int a ...
- JAVA自动装箱拆箱与常量池
java 自动装箱与拆箱 这个是jdk1.5以后才引入的新的内容,作为秉承发表是最好的记忆,毅然决定还是用一篇博客来代替我的记忆: java语言规范中说道:在许多情况下包装与解包装是由编译器自行完成的 ...
- Java 自动装箱/拆箱
自动装箱/拆箱大大方便了基本类型(8个基本类型)数据和它们包装类的使用 自动装箱 : 基本类型自动转为包装类(int >> Integer) 自动拆箱: 包装类自动转为基本类型(Integ ...
- Java自动装箱拆箱
一.装箱.拆箱定义 如果一个int型量被传递到需要一个Integer对象的地方,那么,编译器将在幕后插入一个对Integer构造方法的调用,这就叫做自动装箱.而如果一个Integer对象被放到需要in ...
- 那些年一起踩过的坑 — java 自动装箱拆箱问题
坑在哪里? 我们都知道Java的八种基本数据类型:int, short, long, double, byte, char, float, boolean 分别有各自对应的包装类型:Integ ...
- Java八种基本数据类型的大小,以及封装类,自动装箱/拆箱的用法?
参考:http://blog.csdn.net/mazhimazh/article/details/16799925 1. Java八种基本数据类型的大小,以及封装类,自动装箱/拆箱的用法? 原始类型 ...
- 全面理解java自动装箱和拆箱(转)
自动装箱和拆箱从Java 1.5开始引入,目的是将原始类型值转自动地转换成对应的对象.自动装箱与拆箱的机制可以让我们在Java的变量赋值或者是方法调用等情况下使用原始类型或者对象类型更加简单直接. 如 ...
- java基础1.5版后新特性 自动装箱拆箱 Date SimpleDateFormat Calendar.getInstance()获得一个日历对象 抽象不要生成对象 get set add System.arrayCopy()用于集合等的扩容
8种基本数据类型的8种包装类 byte Byte short Short int Integer long Long float Float double Double char Character ...
- Java的自动装箱/拆箱
概述 自JDK1.5开始, 引入了自动装箱/拆箱这一语法糖, 它使程序员的代码变得更加简洁, 不再需要进行显式转换.基本类型与包装类型在某些操作符的作用下, 包装类型调用valueOf()方法将原始类 ...
随机推荐
- Flutter移动电商实战 --(36)FlutterToast插件使用
https://github.com/PonnamKarthik/FlutterToast fluttertoast: ^3.0.1 category_page.dart页面添加引用 import ' ...
- shell 變數
echo $? 上个命令的退出状态,或函数的返回值. ref: http://c.biancheng.net/cpp/view/2739.html
- 阶段5 3.微服务项目【学成在线】_day03 CMS页面管理开发_10-修改页面-前端-修改页面
1.进入页面,通过钩子方法请求服务端获取页面信息,并赋值给数据模型对象 2.页面信息通过数据绑定在表单显示 3.用户修改信息点击“提交”请求服务端修改页面信息接口 3.3.3 修改页面 3.3.3.1 ...
- Java面试题(基础)
一.Java 基础 1.JDK 和 JRE 有什么区别? 答:JRE是java运行时环境,包含了java虚拟机,java基础类库.是使用java语言编写的程序运行所需要的软件环境,是提供给想运行jav ...
- unittest快速装载目前下所有测试用例的方法
import unittest from BeautifulReport import BeautifulReport #导入BeautifulReport if __name__ == '__mai ...
- MR21修改标准价
转自:https://blog.csdn.net/qq_21813647/article/details/79195731 物料帐下只有物料的状态是初始状态才允许修改价格. 如果状态为已输入数量和值也 ...
- swift 第十三课 GCD 的介绍和使用
手头的项目中基本没有用到这个,但是还是要探索下.毕竟好多的地方要用这个,而且现在手机和电脑等电子设备都是多核心的,这样就成就了多线程带来更加优越的用户体验. 先记录下,自己看到的两个不错的连接: ht ...
- html5 商品分类页面效果zepto
点击左边容器条目,右边列表对应的内容置顶显示,滑动右边的列表,左边容器的对应的标题高亮显示. 效果图如下: 代码: <!doctype html> <html> <hea ...
- 利用matlab自带函数graycoprops 实现基于共生矩阵的遥感图像纹理特征分析
close all;clear all;clc;I = imread('yaogan2.jpg');HSV = rgb2hsv(I);Hgray = rgb2gray(HSV);% 计算64位灰度共生 ...
- elasticsearch启动日志报错not enough master nodes discovered during pinging (found [[]], but needed [-1]), pinging again
排查步骤 逻辑上讲是,一个节点去ping master节点,结果却没有得到回应,多次重试依旧失败.应该重点观察: 1.master启动后,IP是否可以有防火墙权限,设置防火墙规则或则直接关闭防火墙 ...