5

すべて、以下のコードを書くときに問題に直面しました

String hello = "Hello";
String str5 = "Hel" + "lo";
String str8 = "Hel";
String str9 = "lo";
String str10 = str8 + str9;
System.out.println("str10==hello?" + (str10 == hello)); 
System.out.println("str5==hello?" + (str5 == hello));
System.out.println("str10==str5?" + (str10 == str5));

次に、コードを実行すると、コンソールがこれを出力します

str10 == hello ? false
str5 == hello ? true
str10 == str5 ? false

これは私を大いに混乱させました。なぜ 2 番目の出力は TRUE で、最初の出力は FALSE ですか?? 文字列リテラルプールの私の理解では、文字列が定義されている場合、JVMはプールにその文字列が含まれているかどうかを確認し、含まれていない場合は文字列をプールに入れます。
私のコードでは、変数helloが文字列プールに存在し、「Helo」と「lo」もプールに存在します。私の質問は

  1. 「 Helo」と「lo 」を連結した結果がプールに存在する場合。
  2. str5 と str10s の定義の違いは何ですか? また、なぜ "==" ではないのですか? str5 と str10 は、文字列プール内の異なる " Hello " を参照していますか? ("==" 参照が同じオブジェクトであることを意味しているようです)

私のjdkバージョン:1.6.0_29
私のIDE:Intellij Idea 11.2

誰でもそれを指摘できますか?どうもありがとうございます

4

4 に答える 4

7

本来の動作をします。これは、JLS の 2 つのセクションで扱われています。

JLS #3.10.5 :

定数式の値である文字列 (§15.28) - メソッド String.intern を使用して、一意のインスタンスを共有するために「インターン」されます。

JLS #15.28には、定数式と見なされるものがリストされています。特に、文字列リテラルは定数式 ("Hel" および "lo") ですが、変数が定数と見なされるには、それが final である必要があります。

あなたの場合、コードを makestr8およびstr9constant に少し変更すると、次trueの 3 回になります。

final String str8 = "Hel";
final String str9 = "lo";
于 2013-03-15T08:23:43.993 に答える
0

コードには、考慮すべき次の点があります。

String hello = "Hello";

ここで、「Hello」はhelloを参照するために割り当てられたリテラルであるため、リテラルには独自のハッシュコードがあります。

String str5 = "Hel" + "lo";

ここで、「Hel」+「lo」は2つのリテラルが組み合わされ、参照helloに割り当てられているため、新しいリテラルは最初のリテラルと同じであり、したがって同じハッシュコードです。

String str8 = "Hel";
String str9 = "lo";

ここで、str8 + str9は、新しい参照helloを組み合わせて指す2つの参照であるため、新しいリテラルには独自のハッシュコードがあります。

String str10 = str8 + str9;
System.out.println("str10==hello?" + (str10 == hello)); 
System.out.println("str5==hello?" + (str5 == hello));
System.out.println("str10==str5?" + (str10 == str5));

==を使用すると、ハッシュコードと値で一致します。したがって、不一致。

使用してみてください

string_1.equals(string_2)

それ以外の

string_1 == string_2

値の一致のみが得られます。したがって、すべて真実

以下の回答も参照してください(Javaの==とequals()の違いは何ですか?):

equals()メソッドは、2つのオブジェクト参照が同じStringインスタンスを参照しているかどうかに関係なく、(ヒープ上の)Stringインスタンス内の「値」を比較します。String型の2つのオブジェクト参照が同じStringインスタンスを参照している場合は、すばらしいです。two(2)オブジェクト参照が2つの異なるStringインスタンスを参照している場合..違いはありません。比較されている各Stringインスタンス内の「値」(つまり、文字配列の内容)。

一方、 "=="演算子は、2つのオブジェクト参照の値を比較して、それらが同じStringインスタンスを参照しているかどうかを確認します。両方のオブジェクト参照の値が同じStringインスタンスを「参照」する場合、ブール式の結果は「true」になります。一方、両方のオブジェクト参照の値が異なるStringインスタンスを「参照」する場合(両方のStringインスタンスが同じ「値」を持っている場合、つまり、各Stringインスタンスの文字配列の内容が同じである場合でも)ブール式の結果は「false」になります。

于 2013-03-15T08:30:19.960 に答える
-1

2 つの文字列を比較する場合は、string.equalsnotを使用しますstring1 == string2

それを試してみてください:

System.out.println("str10==hello?" + (str10.equals(hello));
于 2013-03-15T08:25:57.377 に答える