Just to clarify, I assume here that the main point of your question was comparing x == z
- two uppercase strings - and not x == y
which would always be false because one is uppercase and the other is lowercase and this has nothing to do with interning.
JVMS 8 5.1 says:
A string literal is a reference to an instance of class String, and is
derived from a CONSTANT_String_info structure (§4.4.3) in the binary
representation of a class or interface. The CONSTANT_String_info
structure gives the sequence of Unicode code points constituting the
string literal.
The Java programming language requires that identical string literals
(that is, literals that contain the same sequence of code points) must
refer to the same instance of class String (JLS §3.10.5). In addition,
if the method String.intern is called on any string, the result is a
reference to the same class instance that would be returned if that
string appeared as a literal. Thus, the following expression must have
the value true:
("a" + "b" + "c").intern() == "abc"
To derive a string literal, the Java Virtual Machine examines the
sequence of code points given by the CONSTANT_String_info structure.
If the method String.intern has previously been called on an instance of class String containing a sequence of Unicode code points
identical to that given by the CONSTANT_String_info structure, then
the result of string literal derivation is a reference to that same
instance of class String.
Otherwise, a new instance of class String is created containing the sequence of Unicode code points given by the CONSTANT_String_info
structure; a reference to that class instance is the result of string
literal derivation. Finally, the intern method of the new String
instance is invoked.
The important parts here is that only string literals are put in a so called string pool and ones on which .intern()
is explicitly called. Same goes to "taking" instances from the string pool. So if a string is created in any other way than specified as a string literal or is recieved from intern()
method, it won't be an instance from string pool nor it will be added there.
A following example shows a little bit better how it works:
String a = "abc".toUpperCase().intern();
String b = "abc".toUpperCase();
String c = "ABC";
String d = "ABC";
System.out.println(a == b); // returns false
System.out.println(a == c); // returns true
System.out.println(b == c); // returns false
System.out.println(c == d); // returns true
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…