私が知っている限り、値の同等性のセマンティクスが必要な場合は、オーバーライドする必要があります。 System.Objectの実装は「悪い」ではなく、参照チェック(そのレベルで実行できるすべての実装)だけです。
要するに、値に基づく等価性(クラスのプロパティに基づく等価性)が必要な場合は、yesを上書きします。それ以外の場合は、既にそれ以上のものでなければなりません。
EDIT: あなただけは、上記のケースでそれらを上書きするを必要としています。あなたが1つをオーバーライドする場合は、明白な理由のために両方をオーバーライドする必要があります(一貫性が必要など)。 は、他の回答(ハッシュ値を使用するアルゴリズムのパフォーマンス、つまりDictionary
キーなど)に記載されているその他の理由ですべてのクラスでそれらをオーバーライドできますが、デフォルトのSystem.Object
の実装は正しく動作します。
EDIT 2: 詳細情報が必要です。現状では
public class User {
private int _id;
private string _username;
public string Username { get {return _username;}};
// [snip] Whatever other properties we might like to have.
public User(string username) {
// Initialise our user from a database, or whatever.
}
}
、次のコードを、直感的に思えるかもしれません:以下の疑似クラスを考えてみましょう
User foo = new User("me");
User bar = new User("me");
User baz = foo;
if (foo.Equals(bar)) {
Console.WriteLine("1: Success!");
}
if (foo.Equals(baz)) {
Console.WriteLine("2: Success!");
}
しかし、それだけでプリントアウトします:
2:成功を
なぜですか? foo
とbar
は、クラスの2つの別々のインスタンスであり、別々の参照を持っています。参照はC/C++のポインタに似ています。 fooとbazは、一方が他方から割り当てられているため、同じ参照です。彼らはすべて同じの値を持っていますが、ユーザーは「私」と呼ばれています。 .Equals
実装をベース値のサンプル実装は次のようになります。
partial class User {
public override bool Equals(object b) {
if (b == null) return false;
if (b.GetType() != this.GetType()) return false;
// Now the heavy lifting
User other = (User)b;
if (other._id == this._id) return true;
else return false;
}
}
は、それが平等を決定するために、クラスのプロパティの一部に対してチェックする方法を参照してください?それは仕事での価値の平等です。参照の平等は単純なthis == b
のチェックに過ぎません。
優秀なポイントを持って平等のためにそれらの項目をテストします。 – Alan