Java 复习笔记6 - 包装类 常量池

概述:

在Java中存在一些基本数据类型,这些基本数据类型变量,不能像其余对象同样调用方法,属性....java

一些状况下带来一些问题,包装类就是为了解决这个问题而出现缓存

image-20191121120735523

包装类可使得这些基础数据类型,拥有对象的能力测试

image-20191121121001152

包装类与基础类型的对应关系

image-20191121120904649

特色:

  • 包装类都是final修饰没法继承
  • 数字类型的父类都是Number
  • 当包装类做为类属性时,其默认值都为Null

拆箱与装箱

拆箱指的是将基础数据类型包装为对象,拆箱与之相反优化

  • 自动装箱code

    将基础数据类型直接赋值给对应包装类的引用变量,系统会自动进行装箱操做对象

    Integer a = 10;
  • 自动拆箱blog

    Integer a = new Integer(10);
    int b = a;
  • 手动拆箱继承

    Integer a = new Integer(10);
    int b = a.intValue();
  • 手动装箱/装箱内存

    Integer as = new Integer(10);//装箱
    Integer.valueOf(1);//装箱
    Float.valueOf(1.1);//装箱
    ....
    
    as.intValue();//拆箱

    一般咱们不须要进行手动拆装箱开发

自动拆箱的时机

1.将包装类型变量直接赋值给对应基础类型时,系统会自动进行拆箱操做

2.当要访问这个对象的真实数据值时会进行自动拆箱,例如要输出对象的值

3.当要对包装类的实际值进行数学运算时,会自动拆箱,例如比较大小

须要注意的是,当使用==判断是否相等时,==符号任意一边是基础数据类型另一边都会自动拆箱(不会出问题),但若是两边都是包装类型则会比较对象引用是否相同(可能产生问题)
Integer i1 = new Integer(10);
Integer i2 = new Integer(10);
System.out.println(i1 == i2); //结果为false

字符串与包装类互相转换

在开发中常常须要将基础数据类型与字符串类型相互转换

//咱们可使用包装类提供的valueof()方法来将字符串转为对象的包装类
System.out.println(Float.valueOf("1.1ff"));
System.out.println(Boolean.valueOf("true"));
//相反的String提供了静态方法valueOf() 其余任意类型转换为字符串类型  Object表示全部类都可,包括包装类
System.out.println(String.valueOf('c'));
System.out.println(String.valueOf(true));

对象常量池

Java虚拟机会默认将一些简单的字面量对象放到常量池中,来减小频繁的内存操做;是一种优化机制;

测试代码:

Long s1 = Long.valueOf(127l);
Long s2 = 127l;
Long s3 = new Long(127l);
System.out.println(s1 == s2); //true
System.out.println(s1 == s3); //false

String st1 = "常量池噢噢噢噢";
String st2 = "常量池噢噢噢噢";
String st3 = new String("常量池噢噢噢噢");
System.out.println(st1 == st2); //true
System.out.println(st1 == st3); //false

Boolean b1 = true;
Boolean b2 = true;
Boolean b3 = new Boolean(true);
System.out.println(b1 == b2); //true
System.out.println(b1 == b3); //false

Character c1 = 'a';
Character c2 = 'a';
Character c3 = new Character('a');
System.out.println(c1 == c2); // true
System.out.println(c1 == c3); // false

Float f1 = 1.0f;
Float f2 = 1.0f;
Float f3 = new Float(1.0f);
System.out.println(f1 == f2);//flase
System.out.println(f1 == f3);//flase

Double d1 = 1d;
Double d2 = 1d;
Double d3 = new Double(1d);
System.out.println(d1==d2);//flase
System.out.println(d1==d3);//flase
  • String类型的全部字面量都会进入常量池
  • Byte Short Integer Long 四种类型字面量在大于等于 -128 且小于等于127 时对象将进入常量池
  • Character 类型 不能为负数,字面量大于等于0 且 小于等于127时对象将进入常量池
  • Boolean类型 两个字面量都会进入常量池
  • Float 和Double 类型 不会进入常量池

强调:

字面量的意思是说,在编译期间就直接指定了实际值,很是明确的数据

这意味着当咱们没有使用字面量而是使用 new关键字时,对象将直接进入堆区而不会进入常量池 ,请看下面的例子:

Integer a1 = new Integer(10);
Integer a2 = new Integer(10);
System.out.println(a1 == a2);  //false

一旦出现了new 则必然要开辟新内存空间,没法利用常量池了!所以建议在代码中尽可能使用字面量避免使用new;
补充说明:
这些包装类,以及String类提供的静态方法valueOf();都会先访问常量池,而不是当即new, 因此使用字面量或者valueOf方法均可以利用常量池;

注意:

基础数据类型不须要缓存到常量池中由于基础数据类型不存在引用这么一说,就是一个实际的值随方法存储在栈区;

相关文章
相关标签/搜索