Java自动装箱与自动拆箱理解

  1. 首先我们要明白什么是基本类型与基本类型的包装类的概念。
        java中的int,byte,long等等都是基本类型;其对应的Integer,Byte,Long等等都是基本类型的包装类。
  1. 自动装箱与拆箱
        基本类型可以使用运算符直接进行计算,但是引用类型不可以,而基本类型包装类作为引用类型的一种却可以计算,这就是因为java中自动为我们做好了Integer转换成int类型,这就是自动拆箱
        相应地,引用数据类型变量的值必须是new出来的内存空间地址值,而我们可以将一个基本类型的值赋值给一个基本类型包装类的引用,这就是因为java中自动为我们做好了int类型转换成Integer类型,这就是自动装箱
Integer i = 5;//自动装箱。相当于Integer i = Integer.valueOf(5);
i = i + 1;//等号右边:将i对象转成基本数值(自动拆箱) i.intValue() + 1; 加法运算完成后,再次装箱,把基本数值转成对象。

    但是我们注意这里有一个坑,因为Integer是引用类型的,所以我们可以将其值设置为null,那么此时如果将null赋值给i,再将i+1就会报错,所以这边就需要去判空。

Integer i = null;
if(i != null){//这里我们经常在写web程序的时候会发生这样的错误
     i = i + 1;
 }else{
     i = 5;
 }
  1. 接下来说说int和Integer的区别吧,面试的时候也经常问到
    (1)Integer是int的包装类;int是基本数据类型;
    (2)Integer变量必须实例化后才能使用;int变量不需要;
    (3)Integer实际是对象的引用,指向此new的Integer对象;int是直接存储数据值 ;
    (4)Integer因为是包装类,属于引用类型,所以其默认值是null;int的默认值是0。
  • 对于Integer来说,他其实是个引用,既然是引用,那么就可以new对象,既然是new的对象,那么两个对象的内存地址就一定不会相同,所以两个变量就不会相等
Integer i = new Integer(100);
Integer j = new Integer(100);
System.out.println(i == j); //false
  • 同样的,如果一个Integer是new出来的,而另外一个Integer不是new出来的,他们的结果也不相同(因为new出来的Integer生成的变量是指向堆中的,而非new生成的Integer是指向java常量池中的对象。那么两者的内存地址就不一样)
Integer i = new Integer(100);
Integer j = 100;
System.out.println(i == j); //false
  • 对于两个非new生成的Integer对象,进行比较时,如果两个变量的值在区间-128到127之间,则比较结果为true,如果两个变量的值不在此区间,则比较结果为false
Integer i = 100;
Integer j = 100;
System.out.println(i == j); //true
/*********************************************/
Integer i = 128;
Integer j = 128;
System.out.println(i == j); //false
/*********************************************/
/*针对以上原因做一个解释:java在编译Integer i = 100 时,会翻译成为Integer i = Integer.valueOf(100),
java中Integer类型的valueOf的定义如下,对于-128到127之间的数,会进行缓存,Integer i = 127时,
会将127进行缓存,下次再写Integer j = 127时,就会直接从缓存中取,就不会new了*/
//以下是valueOf的源码
public static Integer valueOf(int i){
    assert IntegerCache.high >= 127;
    if (i >= IntegerCache.low && i <= IntegerCache.high){
        return IntegerCache.cache[i + (-IntegerCache.low)];
    }
    return new Integer(i);
}
  1. 最后来谈一下valueOf和parseInt的区别(两者的返回类型不同
    (1)Integer.valueOf(String),这个是将String类型转成了Integer对象;
    (2)Integer.parseInt(String),这个是将String类型的对象转成了int类型;
//源码如下
//valueOf中其实是调用了parseInt的方法的。
 public static Integer valueOf(String s) throws NumberFormatException {
   return Integer.valueOf(parseInt(s, 10));
 }
 /***************************************************************/
public static int parseInt(String s) throws NumberFormatException {
   return parseInt(s,10);
 }

猜你喜欢

转载自blog.csdn.net/harryshumxu/article/details/106146042