Java---String类

来源:互联网 发布:mt4编程书籍 编辑:程序博客网 时间:2024/05/23 01:25

String:代表字符串

字符串是常量,其值被创建后不能改变。字符串缓冲区支持可变字符串。因为字符串的值是不可变的,所以可以共享。
那么字符串在内存中是如何存储的呢?且看如下的示例

String str1 = "hello";String str2 = "hello";String str3 = new String("hello");String str4 = new String("hello");System.out.println("str1 == str2:"+(str1 == str2));System.out.println("str2 == str3:"+(str2 == str3));System.out.println("str3 == str4:"+(str3 == str4));System.out.println("str3.equals(str4):"+str3.equals(str4));

输出结果是:
str1 == str2:true
str2 == str3:false
str3 == str4:false
str3.equals(str4):true
在解释为什么会出现上述输出结果之前,首先说一下String在内存中是如何存储的:

  • 利用String str = “hello”;这种方式创建字符串的时候,虚拟机首先去检查字符串常量池中是否存在该字符串的对象,如果存在,那么就不会在字符串常量池中再创建了,直接返回该字符串在字符串常量池中的地址;如果不存在,那么首先在字符串常量池中创建该字符串对象,然后再返回。
  • 利用String str = new String(“hello”);这种方式创建字符串对象的时候,虚拟机首先去字符串常量池中检查该字符串对象是否存在,如果存在,那么就不会在字符串常量池中再创建该字符串对象了;如果不存在,则在常量池中创建该字符串对象,然后还会去堆内存中创建一个字符串对象,并把字符串常量池中的字符串对象的内容拷贝到堆内存中的字符串对象中,然后返回堆内存中该字符串对象的内存地址。

下面用一个图将上述代码在内存中的存储表示出来:
这里写图片描述

根据上图,分析一下四个字符串对象的创建过程:
String str1 = “hello”;
当创建第一个字符串对象str1的时候,首先JVM去检查字符串常量池中是否存在字符串“hello”,此时字符串常量池不存在,那么在字符串常量池中创建“hello”字符串对象(假设存储地址是0x98),然后返回地址0x98;
String str2 = “hello”;
创建第二个字符串对象str2的时候,同样JVM去检查字符串常量池中是否存在字符串“hello”,此时是存在的,则直接返回字符串常量池中字符串对象“hello”的地址即0x98;
String str3 = new String(“hello”);
在创建第三个对象字符串对象str3时,JVM首先会去字符串常量池中检查是否存在字符串对象“hello”,此时是存在的,那么继续去堆内存中创建字符串对象(假设存储地址是0x67),然后将字符串常量池中的字符串对象的内容拷贝到堆内存中,返回地址0x67;
String str4 = new String(“hello”);
在创建str4对象时,同样JVM去字符串常量池中检查是否存在字符串对象“hello”,是存在的,那么继续去堆内存中创建字符串对象(假设存储地址是0x68),然后将字符串常量池中的字符串对象内容拷贝到堆内存中,返回地址0x68



= = 是对两个对象的内存地址进行的比较,所以str1 == str2结果是true,str2 == str3结果是false,str3 == str4结果是false;但是在上一篇Object类的介绍中,equals方法明明也是比较的内存地址,str3和str4的内存地址不一样,为什么结果是true?
这是因为String类重写了Object的equals方法,查看源码会发现重写后的equals方法比对的是字符串的内容是否相等,str3和str4的内容都是”hello”,所以返回true
还有一点要注意,就是将一个字符串对象与字符串常量进行相等比较时,如下str.equals("Hello Wolrd!") 如果str为空,那么在没有进行判断的情况下会报NullPointerException,为了避免这种异常发生且不通过判断,只需要将字符串常量和字符串对象调换一下位置就可以了,即("Hello Wolrd").equals(str) 即使str为空,无需判断则程序也不会报错,通常情况下的这种相等比对,都是将字符串常量置于前面的!
问题:String str = new String(“Hello”);对于上述语句,创建了几个对象?
答:两个对象,一个是存储在字符串常量池中的字符串对象“Hello”,另一个是存储在堆内存中的字符串对象“Hello”

String方法:

构造器:使用字节数组或字符数组构造一个字符串对象
字符数组、字节数组和字符串三者之间是可以相互转换的。
字符串—————>字符数组
char[] buf1 = str.toCharArray();
字符串—————>字节数组
bytes[] buf2 = str.getBytes();
字符数组、字节数组—————>字符串
通过字符串的构造函数即可,其中字符数组、字节数组作为构造函数的参数
调用方法的时候必须保证String对象不为空null,否则将会报空指针异常

原创粉丝点击