IEnumerator <T>Реализация - PullRequest
       50

IEnumerator <T>Реализация

3 голосов
/ 21 октября 2009

У меня есть этот код

public class SomeClass<T>: IEnumerable<T>
{
    public List<SomeClass<T>> MyList = new List<SomeClass<T>>();

    public IEnumerator<T> GetEnumerator()
    {
        throw new NotImplementedException();
    }
}

Как мне извлечь IEnumerator из MyList?

Спасибо, StackoverFlower ....

Ответы [ 5 ]

8 голосов
/ 21 октября 2009

Это:

public List<SomeClass<T>> MyList = new List<SomeClass<T>>();

Должно быть так:

public List<T> MyList = new List<T>();

тогда это должно работать:

public IEnumerator<T> Getenumerator ()
{
  foreach (var item in MyList){
     yield return item;}
}

Вы не можете иметь

List<SomeClass<T>>

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

IEnumerable<SomeClass<T>>

и измените перечислитель на

public IEnumerator<SomeClass<T>> Getenumerator ()
{
  foreach (var item in MyList){
     yield return item;}
}
1 голос
/ 22 октября 2009

Предполагая, что есть способ получить объект T из объекта SomeClass,

public IEnumerator<T> GetEnumerator()
{
    return MyList.Select(ml => ml.GetT() /* operation to get T */).GetEnumerator();
}
1 голос
/ 22 октября 2009

Ответ Кевинса правильный и ленивый (даже лучше). Если вы используете ответ Trodek, будет выброшено следующее исключение:

Cannot implicitly convert type `System.Collections.Generic.List<SomeClass<T>>.Enumerator' to `System.Collections.Generic.IEnumerator<T>'(CS0029)

Тем не менее я хочу добавить комментарий. Когда вы используете yield return , генерируется конечный автомат, который будет возвращать различные значения. Если вы собираетесь использовать вложенные структуры данных (например, деревья), то при использовании yield return будет выделяться гораздо больше памяти, поскольку в каждой подструктуре будет создаваться отдельный конечный автомат.

Ну, это мои два цента!

1 голос
/ 21 октября 2009

Тривиальный вариант будет return MyList.GetEnumerator().

0 голосов
/ 27 июня 2013

В качестве дополнения к принятому ответу, если вы получили сообщение

MyNamespace.MyClass<T>' does not implement interface
  member 'System.Collections.IEnumerable.GetEnumerator()'.
  'WindowsFormsApplication1.SomeClass<T>.GetEnumerator()' cannot implement
  'System.Collections.IEnumerable.GetEnumerator()' because it does not have
  the matching return type of 'System.Collections.IEnumerator'.

Вам необходимо реализовать дополнительный метод GetEnumerator():

System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
{
    return GetEnumerator();
}

IEnumerable<T> реализует IEnumerable, поэтому должны быть реализованы обе формы GetEnumerator().

...