[java基础] java字符串对象的"+"操作

java字符串的"+"操作分为2种:

  1. 字面常量相加: String s1="a"+"b";

  String s2= "a";

  String s3="b";

      2. String对象相加: String s4=s2+s3;  或 String s5=s2+"b";

先说结论:

  1.加号"+"两边任意一边是String对象而非字面常量时,都会在堆区new一个新的String对象出来,并且会检查常量池是否有对应值的对象,如果没有会在常量池创建一个对应值的新对象;有则引用该常量池对象;

  2.如果"+"的两边都是字面常量,则会优先在字符串常量池中寻找相同的值,如果有则引用该对象,否则创建新的String对象并放入常量;

 

 以下是推导出结论的数据和例子:

 1  public static void main(String[] args) {
 2         String s1="ab";
 3         String s2="a"+"b";
 4         String s3="a";
 5         String s4="b";
 6         String s5=s3+s4;
 7         String s6="aba";
 8         String s7=s1+s3;
 9         // false
10         System.out.println(s5==s2);
11         // true
12         System.out.println(s1==s2);
13         // 推测1, 字面常量会被存入String的常量池,而字面常量通过"+"拼接时会被编译器优化为另一个字面常量,如"a"+"b",优化后就是"ab",
14         //因s1已经先声明了,所以String常量池已经有"ab"了,故s2引用的s1是同一个常量池中的对象,所以 s1==s2结果确实为true
15 
16         // 推测2,s5=s3+s4,s3与s4是2个String类型的对象, String对象+String对象的结果等于new 新的String对象,无论该String对象的值是否存储在string常量池中都会在堆中新增一个
17         // 预估 s6==s7为fasle,结果fasle ,符合推测1。推测1通过
18         System.out.println(s6==s7);
19 
20         // 扩展1: String字面常量+String对象了?
21         String s8="abc";
22         String s9=s1+"c";
23         // 结果:false, 推测3,只要 + 的任意一边是String对象,则都会new 新的String对象
24         System.out.println(s8==s9);
25         String s10="a"+s4;
26         // 结果:false, 推测3通过
27         System.out.println(s1==s10);
28 
29         // 扩展2: 如果常量池中已经存2个相同值的对象(1个由2个字面常量相加而创建 ,另一个由String对象"+"操作创建)时,再一次由字面常量相加时是否会创建新的String对象,还是复用原有对象?
// (实际上,常量池中不会存在相同值的对象,通过 "javap -verbose java类名" 可以查看验证常量池的数据。 )
30 String s11="a"+"b"; 31 // 预估:true,结果:true, 32 System.out.println(s1==s11); 33 34 String s12=s3+"b"; 35 // 预估:false,结果:false 36 System.out.println(s1==s12); 37 43 44 }

 

以下是常量池的数据:

[java基础]  java字符串对象的"+"操作

 图中红线部分就是字符串常量池中的数据;

 

参考:

  1. 如何查看java常量池:https://blog.csdn.net/u010741466/article/details/84920253

      2. java字符串常量池:https://www.cnblogs.com/niew/p/9597379.html

 

上一篇:Acwing第776题(字符串移位包含问题)


下一篇:Oracle单表去重复(一)