JAVA String object creation, javastring object
The creation of String objects is special. Normal object creation is performed in the heap, and the String object is not necessarily. Let's look at the code below.
public class StringTest1 {public static void main(String[] args) throws Exception{String a = "abc";String b = "abc";String c = "ab";String d = new String("ab");System.out.println("a=" + a);//a=abcSystem.out.println("b=" + b);//b=abcSystem.out.println("c=" + c);//c=abSystem.out.println("d=" + d);//d=abSystem.out.println("a==b is " + (a == b));//a==b is trueSystem.out.println("c==d is " + (c == d));//c==d is falseField field = String.class.getDeclaredField("value");field.setAccessible(true);char[] valueA = (char[]) field.get(a);char[] valueB = (char[]) field.get(b);char[] valueC = (char[]) field.get(c);char[] valueD = (char[]) field.get(d);System.out.println("a.value(" + valueA.hashCode() + ")=" + Arrays.toString(valueA));//a.value([1829164700)=[a, b, c]System.out.println("b.value(" + valueB.hashCode() + ")=" + Arrays.toString(valueB));//b.value([1829164700)=[a, b, c]System.out.println("c.value(" + valueC.hashCode() + ")=" + Arrays.toString(valueC));//c.value([2018699554)=[a, b]System.out.println("d.value(" + valueD.hashCode() + ")=" + Arrays.toString(valueD));//d.value([2018699554)=[a, b]valueA[0] = 'z';valueD[0] = 'x';System.out.println("a=" + a);//a=zbcSystem.out.println("b=" + b);//b=zbcSystem.out.println("c=" + c);//c=xbSystem.out.println("d=" + d);//d=xb}}
Both a and B are "abc". The test result is that the references of a and B are equal, and the value array is equal. If a is changed first, B also changes.
C and d are both "AB", but the two references are not equal. d is created with new. At this time, an object, a, B, is created in the heap, the three references of c direct to the objects in the constant pool, but the values of c and d below seem to be the same array. c also changes, it indicates that the object created by d in the heap still points to the constant pool, so an object is created with new.
Another classic problem is that String a = "a" + "B"; creates several objects.
Generally, there should be three, a "a", a "B", and a result "AB". Below is a simple class.
public class StringTest2 {@SuppressWarnings("unused")public static void main(String[] args){String a = "a" + "b";}}
Use javap to check the bytecode
javap -c StringTest2.classCompiled from "StringTest2.java"public class test.StringTest2 { public test.StringTest2(); Code: 0: aload_0 1: invokespecial #8 // Method java/lang/Object."<init>":()V 4: return public static void main(java.lang.String[]); Code: 0: ldc #16 // String ab 2: astore_1 3: return}
There is only one instruction ldc #16, and the constant #16 is added from the constant pool. Obviously, this constant is AB, so I will not parse the class file. It should be correct. decompile it directly, the result is:
package test;public class StringTest2{ public static void main(String[] args) { String a = "ab"; }}
So the reference directly points to the constant pool "AB". Is it an object? It may be the result of Compiler optimization, if you have time to parse one byte and one byte of the class file separately, the result should be clearer.