Comments 16
public IEnumerable CountFrom(int start, int limit)
{
for (int i = start; i <= limit; i++)
yield return i;
}
Недавно задумался, не лучше ли будет написать:
public IEnumerable CountFrom(int start, int limit)
{
List res = new List();
for (int i = start; i <= limit; i++)
res.Add( i );
return res;
}
Из плюсов второго подхода мне видится более понятный синтаксис - ясно, во что это превратится после компиляции. Из минусов - полный просчет коллекции может и не понадобится в будущем, с итератором (первый вариант) получается отложенная инициализация. Неясен правда вопрос производительности.
А какие есть еще отличия по использованию этих двух кусков кода?
Собственно минус, который вы упомянули, убивает возможность использования такой конструкции на практике.
UFO just landed and posted this here
«Из минусов — полный просчет коллекции может и не понадобится в будущем, с итератором (первый вариант) получается отложенная инициализация.»
Память, память. В итераторе в каждый момент времени память выделена только под текущий объект и состояние. В списке — сразу подо все.
Для инта это мелочи, а вот для массива документов…
Память, память. В итераторе в каждый момент времени память выделена только под текущий объект и состояние. В списке — сразу подо все.
Для инта это мелочи, а вот для массива документов…
Недавно обнаруженный понятный, но неявный момент:
// вызываем метод с yield return
var list = GetValueListEnumerator();
foreach (var value in list)
{
// что-то делаем
}
// не тут-то было, енумератор закончился!
foreach (var value in list)
{
// еще что-то делаем
}
UFO just landed and posted this here
Стоит ещё отметить, что методы, включающие в себя yield-конструкции, могут возвращать не только IEnumerable, но и IEnumerator. При этом конечные автоматы, генерируемые компилятором, немного отличаются. Подробности можно почитать здесь — csharpindepth.com/articles/chapter6/iteratorblockimplementation.aspx
Sign up to leave a comment.
Реализация итераторов в C# (часть 1)