Почему реализация "IList" требует определения двух методов "GetEnumerator"?

когда я реализую IList<T>, Я считаю, что я должен определить два GetEnumerator методы. One возвращает значение типа IEnumerator, в то время как другой возвращает IEnumerator<T>.

Я немного смущен разницей между этими двумя GetEnumerator методы. Хотя типы возвращаемых данных явно различны, разве они по существу не содержат одни и те же данные?

кроме того, почему это обе версии GetEnumerator может существовать как методы, когда они отличаются только тип возврата? Это, похоже, нарушает правило в C#, которое указывает, что перегруженные методы не может отличаются только типом возвращаемого значения.

6 ответов


оба должны возвращать одни и те же данные, да.

IEnumerator из .Net v1.1, до того, как была введена общая типизация. IEnumerator<T> - это типизированная версия, добавленная в .Net v2.

"старая" версия, IEnumerator, был сохранен для совместимости, так что теперь IList<T> реализует оба.

разница между ними заключается в том, что non-generic IEnumerator возвращает объект, тогда как generic IEnumerator<T> возвращает T. Хотя компилятор c# вставит для вас приведение чтобы сделать non-generic IEnumerator кажется strongly-typed при использовании в foreach.

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


эти два исходят из отдельных интерфейсов, которые реализует IList, поэтому вы должны реализовать оба:

public interface IList<T> : ICollection<T>, IEnumerable<T>, IEnumerable

и они оба могут существовать из-за Явная Реализация Интерфейса.


да, оба метода должны возвращать одни и те же данные.

Они могут сосуществовать, поскольку они являются частью двух разных интерфейсов, IEnumerable и IEnumerable<T>.


они оба могут существовать, потому что один из них будет реализован явно:

IEnumerator IEnumerable.GetEnumerator()
{

}

если вы попытаетесь сделать их как имплицитно определено, вы получите ошибки компиляции.

Да, они оба должны возвращать одни и те же данные.

вы должны определить две версии GetEnumerator для удовлетворения обоих интерфейсов (IEnumerable и IEnumerable<T>), из которых IList<T> происходит. На практике, однако, вы склонны находить неродовая версия GetEnumerator просто вызывает общий в большинстве реализаций.


IList<T> реализует как IEnumerable<T> и IEnumerable. Различные реализации GetEnumerator исходят из каждого из этих интерфейсов. Оба должны возвращать одни и те же данные.


IEnumerator перечисляет объекты, тогда как IEnumerator перечисляет T. Для вашего второго вопроса вторая функция полностью квалифицирована:

  System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()  
  {

  }

vs

public IEnumerator<T> GetEnumerator()
    {

    }