String浅显总结

165 阅读2分钟

学习别人总结记录,比较浅,可能会有问题,欢迎指正。

String、StringBuilder、StringBuffer

  • String 用final修饰,所以String对象是不可修改的。对于 String a = "hello " + "world"; String 并没有改变,只是a的引用地址发生了变化。
  • 字符串引用频繁修改时,使用StringBuilder和StringBuffer,StringBuffer 相对 Stringbuilder来说线程安全(方法使用synchronized修饰)、效率低。所以一般单线程使用Stringbuilder.append()。
  • String相加底层会生成StringBuilder对象,调用append,最后toString返回String对象

String.intern()

前提: intern 作用是,如果当前常量池中不存在该字符串对象,就在常量池中创建字符串对象,并返回引用地址,如果存在,则直接返回引用地址。 hotspot虚拟机实现方法区是通过永久代,jdk1.6运行时常量池存放在永久代,1.7将常量池移到堆中。 jdk1.7,intern() 作用改为,若常量池不存在字符串对象,而堆中存在,则不再在常量池中创建字符串对象,而是直接使用堆中字符串对象引用。

常见面试题

String s1 = new String("abc");这个语句创建了几个对象。 第一个对象,内容"abc",存储在常量池中。 第二个对象,内容"abc",存储在堆中。

String s2 = new String("ab") + new String("ab");这个语句创建了几个对象。 5个对象 堆中:"ab" "ab" "abab"。还有StringBuilder对象 常量池:"ab"。

程序运行看结果

public class Demo {

	public static void main(String[] args) {
		test1();// false true
		test2();// false false            
	}

	public static void test1() {
		String s = new String("1");
		s.intern();
		String s2 = "1";
		System.out.println(s == s2);

		String s3 = new String("1") + new String("1");
		s3.intern();
		String s4 = "11";
		System.out.println(s3 == s4);
	}

	public static void test2() {
		String s = new String("1");
		String s2 = "1";
		s.intern();
		System.out.println(s == s2);

		String s3 = new String("1") + new String("1");
		String s4 = "11";
		s3.intern();
		System.out.println(s3 == s4);
	}

}