In the first case, the compiler knows the value of the String s1. Thus, all strings with the same value will use the same memory locations:
String s1 = "abc";
String s2 = "abc";
Although there are two String references (s1 and s2), there is only one "abc" sequence in memory. The new
operator is not needed because the compiler does the job.
In the second case, the compiler doesn't perform the evaluation of the String value. Thus, the sentence will generate a new instance of String, at runtime:
String s1 = "abc";
String s2 = new String("abc");
The constant "abc" in line 1 references the same memory as the constant "abc" in line 2. But the net effect of line 2 is the creation of a new String instance.