IEquatable Документация сбивает с толку - PullRequest
0 голосов
/ 04 мая 2020

Привет. Я пытаюсь добавить IEquatable в свою программу, и у меня нет никакой подсказки, нужно ли мне добавлять уникальный идентификатор в основном и хэш-код? Они используют номер shd в качестве уникального идентификатора в IEquatable, но дают его значение в конструкторе, и я спросил на этом сайте, нужен ли конструктор, чтобы он выглядел так, как в документации, и я получил нет. Так что теперь я запутался, может кто-нибудь дать мне более простой пример IEquatable, чем документация? вот ссылка на документацию https://docs.microsoft.com/en-us/dotnet/api/system.iequatable-1?view=netcore-3.1 Я просто пытаюсь получить содержимое для работы с настраиваемым списком объектов.

Мой код

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace DataConverter.Objects
{
    public class Category : IEquatable<Category>
    {
       public string _Name { get; set; }
       public string _Id { get; set;}

       private string _HomeCategory { get; set; }  
       public string _prestaId { get; set; }

       public bool _inUse { get; set; }






        public Category(string Name, string Id, string HomeCategory, bool inUse)
        {
            _Name = Name;
            _Id = Id;
            _HomeCategory = HomeCategory;
            _inUse = inUse;

        }

        public bool Equals(Category other)
        {
            if (other == null)
                return false;

            if()
        }
    }
}

1 Ответ

1 голос
/ 04 мая 2020

IEquatable<T> - это просто интерфейс, который сообщает вам, что текущий тип имеет семантику равенства значений, а не ссылку равенства. Что стоит за логикой c, что делает два разных объекта равными или нет, полностью зависит от бизнес-логики c вашего приложения, а не от того, как вы правильно или неправильно реализовали интерфейс.

Что делает две категории быть таким же в вашем домене? Тот же Id? Тогда ваш метод равно:

public bool Equals(Category other)
{
    if (other == null)
        return false;

    return _Id == other._Id;
}

Тот же идентификатор и имя?

public bool Equals(Category other)
{
    if (other == null)
        return false;

    return _Id == other._Id &&
           _Name == other._Name;
}

И так далее. Именно вы решаете, что делает две категории равными друг другу.

Теперь о коде ha sh. Основное правило c, которому должен соответствовать код ha sh: Две равные категории должны иметь одинаковый код ha sh. Обратите внимание, что это не означает, что две категории с один и тот же код ha sh равен, коды ha sh могут конфликтовать, с этим проблем нет вообще. Кроме того, коды ha sh не должны изменяться при изменении объекта, поэтому в идеале они должны основываться на данных, которые нельзя изменить.

Хорошо, как бы вы реализовали свой код ha sh в своем конкретный сценарий?

Случай 1:

public override int GetHashCode() => _Id.GetHashCode();

Случай 2:

public override int GetHashCode() => _Id.GetHashCode() ^
                                     _Name.GetHashCode();

Оба хеша будут соответствовать их Equals аналогам. Единственная проблема заключается в том, что они построены на потенциально изменяемых данных (и у Id, и у Name есть установщики), поэтому, если что-то из этого изменится, ваш хэш-код тоже изменится, и это, как правило, плохая идея.

В зависимости от вашего По сценарию вам, возможно, придется решать эту проблему по-другому. Могут ли ваши данные видоизменяться при выполнении каких-либо операций, чувствительных к ha sh? Например, Линк довольно широко использовал хеши ...

...