Если вы используете .NET 4.0, можно использовать Tuple
класс как в
var tuple = new Tuple<int, int>(17, 42);
var otherTuple = Tuple.Create(17, 42);
и
var list = new List<Tuple<int, int>>();
Обратите внимание, что если вы идете маршрут, используя Tuple<int, int>
, то вам нужно будет для создания пользовательской реализации IEqualityComparer<Tuple<TFirst, TSecond>>
, чтобы отразить ваши правила равенства, которые (x, y)
считаются равными (y, x)
. Затем вам необходимо передать экземпляр этого сравнения в List<T>.Contains(T, IEqualityComparer<T>)
(здесь T
- Tuple<int, int>
для вас).
class TupleAsUnorderedPairComparer : IEqualityComparer<Tuple<TFirst, TSecond>> {
public bool Equals(Tuple<TFirst, TSecond> x, Tuple<TFirst, TSecond> y) {
if(Object.ReferenceEquals(x, y)) {
return true;
}
if(x == null || y == null) {
return false;
}
return x.Item1 == y.Item1 && x.Item2 == y.Item2 ||
x.Item1 == y.Item2 && x.Item2 == y.Item1;
}
public int GetHashCode(Tuple<TFirst, TSecond> x) {
if(x == null) {
return 0;
}
return x.Item1.GetHashCode()^x.Item2.GetHashCode();
}
}
В противном случае, если вы не можете или не хотите использовать Tuple
, то вам нужно будет реализовать IEqualityComparer<Pair>
для Pair
класса или переопределить Object.Equals
и Object.GetHashCode
.
class Pair {
public int First { get; private set; }
public int Second { get; private set; }
public Pair(int first, int second) {
this.First = first;
this.Second = second;
}
public override bool Equals(object obj) {
if(Object.ReferenceEquals(this, obj)) {
return true;
}
Pair instance = obj as Pair;
if(instance == null) {
return false;
}
return this.First == instance.First && this.Second == instance.Second ||
this.First == instance.Second && this.Second == instance.First;
}
public override int GetHashCode() {
return this.First.GetHashCode()^this.Second.GetHashCode();
}
}
и
class PairEqualityComparer : IEqualityComparer<Pair> {
// details elided
}
Если вы используете
list.Contains(pair);
тогда он будет использовать Equals
и GetHashCode
, но если вы используете
list.Contains(pair, new PairEqualityComparer);
, то он будет использовать PairEqualityComparer.Equals
и PairEqualityComparer.GetHashCode
. Обратите внимание, что эти могут быть отличаться от ваших реализаций Object.Equals
и Object.GetHashCode
.
И, наконец, если тестирование на сдерживание - это то, что вы часто будете делать, то List
- не лучший выбор; вы должны использовать класс, предназначенный для этой цели, например, HashSet
.
Я отредактировал мой ответ, чтобы отразить вашу потребность в `(x, y)`, чтобы считаться равным `(y, x)`. – jason 2010-12-04 17:00:29