1.1数据类型
1.1.1基本类型
byte/8
char/16
short/16
int/32
float/32
double/64
long/64
boolen/..
boolean类型只有两个值true和false,可以使用1bit来存储,但是具体大小没有明确规定
Jvm会在编译 时期将boolean类型转换成int,使用1来表示true,使用0来表示false.
Jvm支持boolean数组,但是是通过读写byte数组来实现的.
1.1.2包装类型
基本类型都有相对应的包装类型,基本类型与其对应的包装类之间的赋值使用自动装箱与拆箱完成.
Integer x = 2;//装箱,调用了Integer.valuOf(2)int y = x;//拆箱调用了x.intValue()
装箱:就是将基本类型装换为包装器类型;
拆箱:就是将包装器类型转换为基本类型;
好,问题来来,怎么装箱呢,怎么拆箱呢?
(举例int,integer)
装箱:调用包装器的valuesOf()方法实现的,(具体如何实现,后续添加),使用方法: integer a =10;//装箱
拆箱:调用包装器的intValues()方法,使用方法 int a=10;
1.1.3缓存池
new Integer(123)与Integer.valuOf(123)的区别在于:
new Integer(123)每次都会新建一个对象
Integer.valueOf(123)会使用缓存池中的对象,多次调用同一个对象
Integer x = new Integer(123);Integer y = new Integer(123);
System.out.println(x==y); //false
Integer z =integer.valuesOf(123); integer c = integer.valuesOf(123)
System.out.println(z==c) // true
valueOf()方法的实现比较简单,就是先判断是否在缓存池中,如果在的话,就直接返回缓存池的内容
Java8中,integer的缓存池大小默认为-128--127.
编译器会在自动装箱过程调用valueOF()方法,因此多个值相同且值在缓存值范围内的Integer实例使用自动装箱来创建,那么就会引用相同的对象.
Integer m= 123;Integer n=123;System.out.println(m==n);//true
基本类型对应的缓存池如下:
Boolean values true and flase
All bytes values
Short values between -128 and 127
Int values betwee -128 and 127
Char values between u0000 and u007F
使用这些基本类型对应的包装类型是,如果该数值方位在缓冲池范围内,就可以直接使用缓存池中的对象
1.2String
1.2.1概览
String被声明为final,因此他不可被继承(Integer等包装类也不能被继承)
在Java 8 中,String内部使用char数组储存数据
在Java9之后,String类的是实现改用bytes数组储存字符串,同时使用coder来标识使用了那种编码.
1.2.2不可变的好处
1可以缓存hash值(什么是hash值?是通过对文件内容进行加密运算得到的一组二进制值,主要用于文件校验或者签名)
2String pool
如果一个String对象已经被创建过了,那么就会从String Pool中取得引用,只有String是不可变的,才可能使用String pool.
3安全性
经常作为参数,String不可变性可以保证参数不可变,例如在作为网络连接参数的情况下如果String是可变的,那么在网络连接过程中,String被修改,改变Sting的哪一方以为现在连接的是其他主机,
4线程安全
String的不可变性,使他在多个线程中可以安全使用
1.2.3String StringBuffer StringBuilder
1可变性
String不可变
StringBuffer和StringBuilder是可变的
2线程安全
String是不可变,因此是线程安全的
StringBuffer不是线程安全的
StringBuilder是线程安全的,内部使用synchronized进行同步
1.2.4String Pool
字符串常量池(String Pool)保存着所有所有字符串字面量(literal Strings).这些字面量在编译时期就确定,不仅如此,还可以使用String的intern()方法在运行过程将字符串添加到String pool中.
当一个字符串调用intern()方法是,如果String pool中已经存在一个字符串和该字符串值相等(方法内部使用equals()进行确定),那么就会返回String Pool中字符串的引用;否则就会在String pool中添加一个新的字符串,并返回这个新字符串的引用.
String s1 = new String(“aaa”);
String s2 = new String(“aaa”);
System.out.println(s1==s2);//false;
String s3=s1.intern();
String s4=s1.intern();
System.out.println(s3==s4);//true
使用new String()创建了两个不同的字符串,而s3和s4是通过S1.intern()方法取得同一个字符串引用,intern()首先把S1引用的字符串放入到String Pool中,然后返回指这个字符串引用,因此s3和s4引用的是同一个字符串
如果是采用”bbb”这种字面量的形式创建字符串,会自动地将字符串放入String pool中
String s5 =”bbb”;
String s6 =”bbb”;
System.out.println(s5==s6);//true
1.2.5new String(“abc”)
使用这种方式一共会创建两个字符串对象(当然前提是String pool 中还没有”abc”字符串对象)
“abc”属于字符串字面量,因此在编译时期会在String pool中创建一个字符串对象,指向这个”abc”字符串字面量;
而使用new的方式会在堆中创建一个符串对象.