Equals
Метод Ecuals
Поведение метода Equals по умолчанию:
Реализация метода Equals:
Основные причины для переопределения метода  Equals для своего типа:
Правила переопределения метода  Equals :
Пример переопределения метода Equals
Метод GetHashCode
Метод GetHashCode
Алгоритм работы метода GetHashCode
Пример реализации метода GetHashCode
Правила переопределения метода GetHashCode:
143.00K
Категория: ПрограммированиеПрограммирование

Equals. Метод Ecuals

1. Equals

Виртуальные методы
Equals
GetHashCode

2. Метод Ecuals

Виртуальный метод Equals определен в типе System.Object и
доступен всем типам.
Метод Equals() проверяет два объекта на равенство и
возвращает true, если оба объекта равны;
Сигнатура метода: bool Object.Equals(Object value);
public static void Main(string[] args)
{
object x = 5;
object y = 5;
Console.WriteLine(x.Equals(y)); //true
}

3. Поведение метода Equals по умолчанию:

Для ссылочных типов -> true, если ссылки совпадают.
Для значимых типов -> true, если совпадают тип и значение.
string - это особый случай. Он ведет себя как тип значения.
Для структур – эквивалентность для каждого поля.
Объект равный null, выбросит исключение
NullReferenceException;
Метод можно переопределить или реализовать один из
подходящих интерфейсов.

4. Реализация метода Equals:

public virtual bool Equals(object other)
{
var this.Ref = GetReference(this);
var other.Ref = GetReference(other);
if (this.Ref == other.Ref)
{
return true;
}
return false;
}

5. Основные причины для переопределения метода  Equals для своего типа:

Основные причины для переопределения
метода Equals для своего типа:
Изменение семантики эквивалентности;
Ускорение процесса сравнения структур.
public virtual bool Equals(object obj);
возвращает true, если параметр и вызывающий объект
ссылаются на одну и туже область памяти;
public static bool Equals(object ob1, object ob2);
возвращает true, если оба параметра ссылаются на одну и ту
же область памяти;

6. Правила переопределения метода  Equals :

Правила переопределения метода Equals :
Сравнение с null: объект не может быть равен null (за
исключением Nullable типов)
x.Equals(null) == false;
Рефлексивно:
x.Equals(x) == true;
Симметрично: реализация должна быть коммутативной,
если a.Equals(b) ==true, то b.Equals(a) == true;
Транзитивно:
a.Equals(b) == true,
b.Equals(c) ==true ,
a.Equals(c) == true;
Согласовано: метод должен быть повторяем и надежен.

7. Пример переопределения метода Equals

// сравнение значений, а не ссылок
public override bool Equals( object obj )
{
if ( obj == null || GetType() != obj.GetType() )
return false;
Monster temp = (Monster) obj;
return health == temp.health &&
ammo == temp.ammo &&
name == temp.name;
}
public override int GetHashCode()
{
return name.GetHashCode();
}

8. Метод GetHashCode

Является виртуальным методом типа object.
Используется в двух коллекциях:
System.Collections.Hashtable
System.Collections.Generic.Dictionary<TKey,TValue>
Возвращает значение хеш-функции объекта, который может
использоваться в алгоритмах хэширования и хэш-таблицах.
Хэш-код - целое знаковое 32 битное число.

9. Метод GetHashCode

В ссылочных и значимых типах имеют стандартную реализацию
метода.
Для хэш-функции должны использоваться только те поля,
которые используются в Equals методе.
Метод переопределяется в случае, если переопределяется
Equals() (необходимо для корректной работы с объектами
класса Hashtable (Хэш-таблица).

10. Алгоритм работы метода GetHashCode

public (bool, TValue) Get(TKey key)
{
var hashCode = key.GetHashCode();
var index = Math.Abs(hashCode % _storageSize);
var values = _storage[index];
for (var i = 0; i < values.Length; ++i)
{
var (storedKey, value) = values[i];
if (storedKey.Equals(key))
{
return (true, value);
}
}
return (false, default);
}

11. Пример реализации метода GetHashCode

class Person
{
public string Name { get; set; } = "";
public override int GetHashCode()
{
return Name.GetHashCode();
}
}
public virtual int GetHashCode()
{
if (_hashCode)
return _hashCode;
_hashCode = GenerateNewHashCode(_threadId);
return _hashCode;
}

12. Правила переопределения метода GetHashCode:

Совместимо с 'Equals‘: должен возвращаться одинаковый хэшкод для
любых двух объектов, для которых вызов Equals возвращает true;
Не должен генерировать исключение.
Должен возвращаться одинаковый хэш-код для одного и того же
объекта вне зависимости от количества вызовов метода GetHashCode ;
Необходимо минимизировать вероятность возвращения одного и того
же хэш-кода для двух различных объектов (для получения
максимальной производительности).
Всегда необходимо переопределять Equals и GetHashCode, чтобы
избежать снижения производительности.
English     Русский Правила