Что не так с моим List‹T›.Distinct()?

У меня есть класс MyItems, который реализует IEqualityComparer и переопределяет следующие методы:

public bool Equals(MyItems item1, MyItems item2)
{
    return (item1.ID == item2.ID && item1.itemName.Equals(item2));
}
public int GetHashCode(MyItems item)
{
    return item.ID.GetHashCode() ^ item.itemName.GetHashCode();
}

Во-первых, зачем нужно GetHashCode? Я понимаю переопределение метода Equals, однако необходимость GetHashCode ускользнула от меня.

Во-вторых, похоже, это не работает. Есть ли что-то, что я делаю неправильно здесь? Где я не понимаю GetHashCode,, что, возможно, где я спотыкаюсь.


person B-Rad    schedule 02.01.2013    source источник
comment
return (item1.ID == item2.ID && item1.itemName.Equals(item2.**itemName**));   -  person I4V    schedule 03.01.2013
comment
Если ваш класс MyItems сам реализует IEqualityComparer<MyItems>, что-то не так. Либо: переопределить Equals(object) (один параметр) и переопределить GetHashCode() (ноль параметров). Или: Напишите другой класс для сравнения MyItems; лучший способ — наследоваться от абстрактного класса EqualityComparer<>.   -  person Jeppe Stig Nielsen    schedule 03.01.2013


Ответы (3)


Чтобы ответить на свой первый вопрос, просто посмотрите здесь для получения дополнительной информации.

Чтобы ответить на ваш второй вопрос: вы забыли, что item2 должен быть item2.itemName

return (item1.ID == item2.ID && item1.itemName.Equals(item2.itemName));
person Corey Adler    schedule 02.01.2013
comment
Спасибо тебе за это! Довольно неловко, хотя и не редкость для меня, пропустить что-то подобное! - person B-Rad; 03.01.2013

Метод Distinct работает следующим образом:

  1. Проверьте, имеют ли два объекта одинаковый хеш-код, используя GetHashCode.
  2. Если да, убедитесь, что они абсолютно равны Equals.

GetHashCode — это первый чек для более дорогого чека: Equals

В вашем методе Equals есть ошибка:

return (item1.ID == item2.ID && item1.itemName.Equals(item2));

Должно быть:

return (item1.ID == item2.ID && item1.itemName.Equals(item2.itemName));
//                                                         ^^^^^^^^^

Кроме того, если тип списка или массива, который вы используете, не относится к типу <MyItems>, вам также необходимо переопределить метод Equals.

person gdoron is supporting Monica    schedule 02.01.2013

Если вы хотите сравнить объекты, вы должны переопределить Equals(object obj) в их классе.

Кроме того, всякий раз, когда вы переопределяете Equals(object obj), рекомендуется переопределять GetHashCode.

person Alexandar    schedule 02.01.2013