次のコードのような:
int age = 25; short newAge = 25; Console.WriteLine(age == newAge); //true Console.WriteLine(newAge.Equals(age)); //false Console.ReadLine();
int と short はプリミティブ型ですが、「==」との比較は true を返し、equals() は false を返します。なぜ?
答え:
要するに:
"equals()" は "==" よりも複雑です。
具体的には:
元の型は、基本クラスの object.Equals(object) をオーバーライド (オーバーライド) し、括弧内のオブジェクトがその型および値と同じである場合に true を返します (Nullable 型も、上記の判断。空でない Nullable 型は常に基本型インスタンスにボックス化されます。
newAge が短いため、 object が短く、値が newAge 値と等しい場合、 newAge.Equals(object) は true を返します。渡しているのは int オブジェクトなので、false を返します。
対照的に、「==」演算子は、2 つの整数 (int)、2 つの短整数 (short)、または 2 つの長整数 (long) を使用する演算として定義されます。 「==」の 2 つのパラメーターが integer と short integer の場合、コンパイラーは暗黙的に short を int に変換し、変換された int 値のサイズを比較します。
それを機能させるための他の方法:
プリミティブ型にも独自のequals()メソッドがあり、equalsは同じ型のパラメータを受け入れます。
age.Equals(newAge) を記述すると、コンパイラーは int.Equals(int) を最適なオーバーロード メソッドとして選択し、暗黙的に short を int に変換します。このメソッドは 2 つの int 値のサイズを直接比較するため、true が返されます。
shortにもshort.Equals(short)メソッドがありますが、int型は暗黙的にshortに変換できないので呼び出されません。
キャスト変換を使用してこのメソッドを強制的に呼び出すことができます:
Console.Writeline(newAge.Equals((short)age)); //true
これは、ボクシング操作を行わずに short.Equals(short) を直接呼び出します。 age が 32767 より大きい場合、オーバーフロー例外がスローされます。
short.Equals(object) オーバーロードを呼び出すこともできますが、同じ型のボックス化されたオブジェクトを明示的に渡す必要があります:
Console.WriteLine(newAge.Equals((object)(short)age)); // true
前のオプションのメソッド (short.Equals(short)) と同様に、サイズが超過した場合短い範囲では、オーバーフロー例外もスローされます。以前のソリューションとは異なり、オブジェクトを短くボックス化するため、時間とメモリが無駄になります。
ソースコード:
実際に使用されるEquals()は次のとおりです:
public override bool Equals(Object obj) { if (!(obj is Int16)) { return false; } return m_value == ((Int16)obj).m_value; } public bool Equals(Int16 obj) { return m_value == obj; }
C#の==とequals()の違いに関連するその他の記事については、 PHPの中国語サイトです!