Список <T> .Contains и T []. Содержит поведение по-разному

Скажем, у меня есть этот класс:

public class Animal : IEquatable
{
    public string Name { get; set; }

    public bool Equals(Animal other)
    {
        return Name.Equals(other.Name);
    }
    public override bool Equals(object obj)
    {
        return Equals((Animal)obj);
    }
    public override int GetHashCode()
    {
        return Name == null ? 0 : Name.GetHashCode();
    }
}

Это тест:

var animals = new[] { new Animal { Name = "Fred" } };

Теперь, когда я делаю:

animals.ToList().Contains(new Animal { Name = "Fred" }); 

это называет правильнымобщийEquals перегрузки. Проблема с типами массивов. Предположим, я делаю:

animals.Contains(new Animal { Name = "Fred" });

это вызываетне общийEquals метод. На самом делеT[] Безразлично»разоблачитьICollection.Contains метод. В приведенном выше случаеIEnumerable.Contains перегружается расширение, которое в свою очередь вызываетICollection.Contains, Вот какIEnumerable.Containsреализовано:

public static bool Contains(this IEnumerable source, TSource value)
{
    ICollection collection = source as ICollection;
    if (collection != null)
    {
        return collection.Contains(value); //this is where it gets done for arrays
    }
    return source.Contains(value, null);
}

Итак, мои вопросы:

Зачемдолжен List.Contains а такжеT[].Contains вести себя по-другому? Другими словами, почему бывший называетобщийEquals ипоследний неуниверсальныйEquals хотя обе коллекции являются общими?Есть ли способ, которым я могу видетьT[].Contains реализация?

Редактировать: Почему это важно или почему я спрашиваю это:

Это отключает один на тот случай, если она забудет переопределитьне общийEquals при реализацииIEquatable в этом случае звонки какT[].Contains делает проверку ссылочного равенства. Особенно когда она ожидаетвсе общие коллекции работать науниверсальныйEquals

Вы теряете все преимущества реализацииIEquatable (хотя это некатастрофа для справочных типов).

Как отмечается в комментариях, просто интересно знать внутренние детали и выбор дизайна. Там нет другой общей ситуации, я могу думать о том, гдене общийEquals будет предпочтительным, будь то любойList или установить на основе (Dictionary и т. д.) операции. Еще хуже,Если Animal был структурой, Animal []. Содержит вызовыобщийEqualsВсе, что делает реализацию T [] странным, то, что разработчики должны знать.

Замечания: Общая версияEquals вызывается только когда классреализуетIEquatable Если класс нереализоватьIEquatableнеуниверсальная перегрузкаEquals называется независимо от того, называется ли онList.Contains или же .T[].Contains

Ответы на вопрос(3)

Ваш ответ на вопрос