Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/312.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 字符串比较混乱_Java_String - Fatal编程技术网

Java 字符串比较混乱

Java 字符串比较混乱,java,string,Java,String,在我们继续之前: 我知道我们应该使用.equals()来比较内容。我现在只是在谈论以下场景的实际引用是否相同… 假设我们有以下几点: String str1 = "str"; String str2 = "string"; String str3 = "ing"; String str4 = str1 + str3; str1 = str4; String str5 = "string"; System.out.println(str1==str2);//false 我认为这应该是真的,因为在

在我们继续之前: 我知道我们应该使用.equals()来比较内容。我现在只是在谈论以下场景的实际引用是否相同…

假设我们有以下几点:

String str1 = "str";
String str2 = "string";
String str3 = "ing";
String str4 = str1 + str3;
str1 = str4;
String str5 = "string";
System.out.println(str1==str2);//false
我认为这应该是真的,因为在字符串池中,对“String”的引用应该是相同的,因为str1和str2现在都是“String”。它应该是真的,但最终为

System.out.println(str1.intern()==str2.intern());//true
我试过了,这次它返回了一个真的。 然后我试着:

System.out.println(str1==str5);//false
System.out.println(str2==str5);//true
System.out.println(“str”+“ing”=“string”)//正确

那不是应该来自琴弦池吗? 有人能帮我解释一下吗?

只有字符串文字和常量表达式才能保证合并。由于str1+str2不是一个文本,因此结果是否被保存取决于JVM。您可以通过调用
intern()
强制它,正如您已经发现的那样

定义如下:

字符串文字是对类
string
(§4.3.1,§4.3.3)实例的引用

此外,字符串文本总是引用类
string
的同一实例。这是因为使用方法
string.intern
,字符串文字(或者更一般地说,是常量表达式(§15.28)的值的字符串)被“插入”以共享唯一实例

您的第二个示例,
“str”+“ing”
,是一个常量表达式,因此它保证是内部的

另见

这是试图解释发生了什么。编写良好的代码可能永远不会依赖于此,而是始终使用
equals
方法。任何合理的JRE都会有如下检查

if (this == other)
  return true;

非常接近
字符串的顶部。equals
因此性能方面,这应该无关紧要。

始终使用equals方法比较字符串。interning的问题在于,JDK的每个版本都有一点不同,因此我不会指望它,除非您每次都想在字符串上调用intern。

比较如下:

String str1 = "str";`   //"str" is created in SCP and str1 is a reference to that    
String str2 = "string";` //"string" is created in SCP and str2 is a reference   
String str3 = "ing";`  //"ing" is created in SCP and str3 is a reference    
String str4 = str1 + str3;//"string" will be created on Heap and str4 is a reference (this is because if any string created at runntime will always be created on Heap) (here SCP already has this "string" so no change) make a note      that str4 is pointing to Heap string Object and not SCP   

str1 = str4; `// str1 and str4 will start pointing to same String Object on Heap    
String str5 = "string";`  // SCP already has this and str2 pointing to that so now onwards str5 will also point to it   

based on above    
1. str1 and str4 -- > are pointing to "string" object on heap    
2. str2 and str5 -- > are pointing to "string" object in scp  
3. str3 -- > is pointing to "ing" in scp   

and finally the corresponding output can be traced based on above lines:

System.out.println(str1==str2);`//false   
System.out.println(str1.intern()==str2.intern());`//true   
System.out.println(str1==str5);`//false   
System.out.println(str2==str5);`//true   
System.out.println("str"+"ing"=="string");`//true as "str"+"ing" will be replaced by "string" at compile time only (constant)

System.out.println(str1.intern()==str2.intern())不应返回true。。。文本是不同的。
String
final
,这意味着它是不可变的。更改文本,创建一个新对象。可能重复的str1和str2都有相同的文本。@user2040251虽然这是有趣的背景,但它不回答为什么编译时常量字符串不是interned我认为这是答案,但您是否有任何来源支持此上升趋势。我理解.equals()的用法。我只想找出这个场景中的引用问题。