2

私は class を持ってPairいます。これは、格納する 2 つの値が交換可能であるため、オーバーライドされた等値演算子を持つ必要があります。コードは次のとおりです。

Pair.cs

public class Pair
    {
        protected bool Equals(Pair other)
        {
            return (Equals(A, other.A) && Equals(B, other.B)) || (Equals(A, other.B) && Equals(B, other.A));
        }

        public override bool Equals(object obj)
        {
            if (ReferenceEquals(null, obj)) return false;
            if (ReferenceEquals(this, obj)) return true;
            return obj.GetType() == this.GetType() && Equals((Pair) obj);
        }

        public override int GetHashCode()
        {
            unchecked
            {
                return ((A != null ? A.GetHashCode() : 0)*397) ^ (B != null ? B.GetHashCode() : 0);
            }
        }

        public readonly Collision A, B;

        public Pair(Collision a, Collision b)
        {
            A = a;
            B = b;
        }

        public static bool operator ==(Pair a, Pair b)
        {
            if (ReferenceEquals(a, b))
                return true;

            if ((object)a == null || (object)b == null)
                return false;

            return (a.A == b.A && a.B == b.B) || (a.A == b.B && a.B == b.A);
        }

        public static bool operator !=(Pair a, Pair b)
        {
            return !(a == b);
        }
    }

ReSharper にEqualsandGetHashCodeメソッドを追加してもらいました。問題ないことEqualsはわかっていますがGetHashCode、正しい値を出力していますか?

ペアをHashSet<Pair>保存するために使用する があり、このリストに重複がないことを確認する必要がありますが、ペアを に追加してHashSetも重複は削除されません。

明確にするために、これは重複します:

Pair a = new Pair(objecta, objectb);
Pair b = new Pair(objectb, objecta);
HashSet<Pair> pairs = new HashSet<Pair>();
pairs.Add(a);
pairs.Add(b);
return pairs.Count(); //Count() returns 2 when it should be 1!
4

2 に答える 2

3

あなたのGetHashCode実装は、(A, B) と (B, A) に対して同じ値を返しません。はHashSet、挿入時に特定のハッシュが既に含まれているかどうかをチェックします。そうでない場合、オブジェクトは新規と見なされます。

を修正するGetHashCodeと、2 番目を挿入した時点で、PairHashSetハッシュ コードが既に存在することを確認し、同じハッシュ コードを共有する他のオブジェクトとの等価性を検証します。

于 2013-06-04T02:03:33.140 に答える
2

これを削除するだけです: *397

重複と見なされる場合は、 GetHashCode() から同じ int を返す必要があります。(ただし、重複と見なされない場合でも、同じ int を返すことができますが、これはパフォーマンスにのみ影響します)。

于 2013-06-04T02:01:46.550 に答える