一个String相加的神奇问题

时间:2021-02-23 19:55:07
大家好,问个很神奇的问题。欢迎讨论。。
代码1:
String str1 = "a";
String str2 = "b";
String str3 = "ab";
String str4 = str1 + str2;

System.out.println(str3 == str4);

代码2:
String str1 = "ab";
String str2="a"+"b";
System.out.println(str1  == str2);


结果代码1打印了false   代码2打印了true       

有高人出来解释下吗?      谢谢了~~

11 个解决方案

#1


楼主你比较的是字符串地址,如果是比较内容的话应该用equals 一个String相加的神奇问题

#2


编译器会做优化的,比如 int i=2+3 那么实际字节码就是 int i=5 而不是在运行期再算一遍

#3


1L说的很清楚,你比较的是地址,关于第二个代码2L也说的很清楚,编译器的优化,Str2=”a“+”b“ 对于编译器来说其实就是Str2=“ab”,压根就不算拼接

#4


String str1 = "a";
String str2 = "b";
String str3 = "ab";
String str4 = str1 + str2;

System.out.println(str3 == str4);

其实,“a”、"b"、"ab"这三个都是在字符串池中创建的,而str1、str2、str3、str4这些都是存在于堆空间的地址,指向于字符串池中的字符串。  当你比较str3==str4的时候,比较的并不是字符串池中的 字符串,而是存在于堆空间的地址..所以是false..当然,如果想要为true也容易,用equals就是.


String str1 = "ab";
String str2="a"+"b";
System.out.println(str1  == str2);

这两个的区别就是你后面的赋值,你是直接把str1和str2同时指向了字符串池中的"ab"。所以他们两个的地址是一样的~ so, true

希望能对楼主有帮助,别被我说晕了啊~ 哈哈

#5


http://www.eoeandroid.com/forum.php?mod=viewthread&tid=335088&page=1#pid4051788      这个是我在eoe发的帖子。   是同一个问题。     请大家看下。        有人说String s=new String("aaa");  会在普通对象堆中和字符串永久区中都创建一块“aaa”的内存。   不知道有没有人有异议。   谢谢大家回答!

#6


他们所指向的地址不同

#7


代码1 的 string1  string2 在不同的堆上,代码2的 string2 是在同一个堆上进行的操作

#8


代码2在编译时就已经处理了

#9


java比字符串值是否相同用的是.equals()
代码2打印true的原因是编译器优化

#10


第一个是地址不同  所以返回false; 第二个是由于相加后发现string池中有相同的字符串  所以不会再开一个地址~   所以地址是相同的  所以返回true

#11


引用 4 楼 shijing266 的回复:
String str1 = "a";
String str2 = "b";
String str3 = "ab";
String str4 = str1 + str2;

System.out.println(str3 == str4);

其实,“a”、"b"、"ab"这三个都是在字符串池中创建的,而str1、str2、str3、str4这些都是存在于堆空间的地址,指向于字符串池中的字符串。  当你比较str3==str4的时候,比较的并不是字符串池中的 字符串,而是存在于堆空间的地址..所以是false..当然,如果想要为true也容易,用equals就是.


String str1 = "ab";
String str2="a"+"b";
System.out.println(str1  == str2);

这两个的区别就是你后面的赋值,你是直接把str1和str2同时指向了字符串池中的"ab"。所以他们两个的地址是一样的~ so, true

希望能对楼主有帮助,别被我说晕了啊~ 哈哈

解释的很详细,顶一下

#1


楼主你比较的是字符串地址,如果是比较内容的话应该用equals 一个String相加的神奇问题

#2


编译器会做优化的,比如 int i=2+3 那么实际字节码就是 int i=5 而不是在运行期再算一遍

#3


1L说的很清楚,你比较的是地址,关于第二个代码2L也说的很清楚,编译器的优化,Str2=”a“+”b“ 对于编译器来说其实就是Str2=“ab”,压根就不算拼接

#4


String str1 = "a";
String str2 = "b";
String str3 = "ab";
String str4 = str1 + str2;

System.out.println(str3 == str4);

其实,“a”、"b"、"ab"这三个都是在字符串池中创建的,而str1、str2、str3、str4这些都是存在于堆空间的地址,指向于字符串池中的字符串。  当你比较str3==str4的时候,比较的并不是字符串池中的 字符串,而是存在于堆空间的地址..所以是false..当然,如果想要为true也容易,用equals就是.


String str1 = "ab";
String str2="a"+"b";
System.out.println(str1  == str2);

这两个的区别就是你后面的赋值,你是直接把str1和str2同时指向了字符串池中的"ab"。所以他们两个的地址是一样的~ so, true

希望能对楼主有帮助,别被我说晕了啊~ 哈哈

#5


http://www.eoeandroid.com/forum.php?mod=viewthread&tid=335088&page=1#pid4051788      这个是我在eoe发的帖子。   是同一个问题。     请大家看下。        有人说String s=new String("aaa");  会在普通对象堆中和字符串永久区中都创建一块“aaa”的内存。   不知道有没有人有异议。   谢谢大家回答!

#6


他们所指向的地址不同

#7


代码1 的 string1  string2 在不同的堆上,代码2的 string2 是在同一个堆上进行的操作

#8


代码2在编译时就已经处理了

#9


java比字符串值是否相同用的是.equals()
代码2打印true的原因是编译器优化

#10


第一个是地址不同  所以返回false; 第二个是由于相加后发现string池中有相同的字符串  所以不会再开一个地址~   所以地址是相同的  所以返回true

#11


引用 4 楼 shijing266 的回复:
String str1 = "a";
String str2 = "b";
String str3 = "ab";
String str4 = str1 + str2;

System.out.println(str3 == str4);

其实,“a”、"b"、"ab"这三个都是在字符串池中创建的,而str1、str2、str3、str4这些都是存在于堆空间的地址,指向于字符串池中的字符串。  当你比较str3==str4的时候,比较的并不是字符串池中的 字符串,而是存在于堆空间的地址..所以是false..当然,如果想要为true也容易,用equals就是.


String str1 = "ab";
String str2="a"+"b";
System.out.println(str1  == str2);

这两个的区别就是你后面的赋值,你是直接把str1和str2同时指向了字符串池中的"ab"。所以他们两个的地址是一样的~ so, true

希望能对楼主有帮助,别被我说晕了啊~ 哈哈

解释的很详细,顶一下