Почему перечислитель списка <T> является общедоступным?

В чем причина модификатора открытого доступа в списке Enumerator в List?

Я бы ожидал, что private-модификатор не будет публичным.

Список исходного кода

Ответ 1

Он общедоступен, так что GetEnumerator() может быть объявлен для его возврата.

Это позволяет компилятору С# использовать его в цикле foreach... избегая выделения кучи, поскольку List.Enumerator является структурой. (Изменчивая структура, которая заставляет меня идти "ура!", Но это другая история.)

Поэтому, когда у вас есть что-то вроде:

List<string> list = new List<string> { "..." };
foreach (var item in list)
{
    Console.WriteLine(item);
}

Затем компилятор может преобразовать его во что-то вроде:

List<string> list = new List<string> { "..." };
using (List<string>.Enumerator enumerator = list.GetEnumerator())
{
    while (enumerator.MoveNext())
    {
        string item = enumerator.Current;
        Console.WriteLine(item);
    }
}

Обратите внимание на тип enumerator здесь - тогда как если бы мы имели:

IEnumerable<string> list = new List<string> { "..." };
foreach (var item in list)
{
    Console.WriteLine(item);
}

было бы использовать:

using (IEnumerator<string> enumerator = list.GetEnumerator())

... который включает в себя выделение кучи, так как IEnumerator<string> является ссылочным типом. Реализация IEnumerable<T> метода GetEnumerator() в List<T> возвращает упакованный List<string>.Enumerator.

Ответ 2

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

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