安全和性能考虑(字符串常量池)是String类不可变的主要原因。
案例
- 字符串对象被缓存在字符串池中,缓存的字符串被多个客户端共享,这时如果字符串可变。那么某个客户端修改了字符串的值会影响到其它的客户端。字符串的缓存从性能原因来考虑,设计为不可变又是非常重要的。
像下面这样字符串one和two都用字面量"something"赋值。它们其实都指向同一个内存地址。
String one = "someString";
String two = "someString";
字符串线程池
- 字符串在许多java的类中被广泛使用。在网络连接中,你可以传递主机名和端口号作为字符; 在数据库连接中,你可以传递数据库地址作为字符串; 在File I/O中,你可以通过字符串文件名来打开任何文件。
这种情况下,如果字符串不是不可变的,将会导致严重的安全问题。一些人可以访问任何文件,一旦他有了授权,他可以故意的修改文件名,或者无意的获取到另外一个文件的访问权限。
- 在多线程编程中,因为String是不可变的,你就无需考虑字符串的同步问题。不可变性让字符串变的线程安全。
注意:SubString导致的内存泄漏,虽然不是线程问题,但是也要注意
面试题
- String a= “abc” String b = “abc” String c = new String(“abc”) String d = “ab” + “c” .他们之间 == 较的结果.
String a = "abc";
String b = "abc";
String c = new String("abc");
String d = "ab" + c;
System.out.println("a == b?" + (a == b));
System.out.println("a == c?" + (a == c));
System.out.println("a == d?" + (a == d));
System.out.println("b == c?" + (b == c));
System.out.println("b == d?" + (b == d));
System.out.println("c == d?" + (c == d));
// 输出结果
a == b?true
a == c?false
a == d?false
b == c?false
b == d?false
c == d?false
网友评论