Реализация Итераторов В C# (Часть 2)

Реализация итераторов в C# (часть 1) .

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

Вот сценарий, основанный на реальных событиях: У меня есть большой и сложный итератор, и я хочу его реорганизовать.

Для большей наглядности условимся, что перечислитель считает от 1 до 100 дважды.

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

)

  
  
   
    

IEnumerable<int> CountTo100Twice() { int i; for (i = 1; i <= 100; i++) { yield return i; } for (i = 1; i <= 100; i++) { yield return i; } }

Как мы знаем из «Программирование 101», мы можем поместить общий код в подпрограмму и вызвать ее.

Но когда я это делаю, я получаю ошибку компилятора:

IEnumerable<int> CountTo100Twice() { CountTo100(); CountTo100(); } void CountTo100() { int i; for (i = 1; i <= 100; i++) { yield return i; } }

Что я делаю не так? Как переместить «счет до 100» в подпрограмму и дважды вызвать ее из функции CountTo100Twice? Как мы только что видели, итераторы вообще не являются подпрограммами.

Представленная выше техника отлично работала бы, если бы мы создавали итераторы, скажем, из волокон, а не из конечных автоматов.

Но поскольку используются автоматы, выражения доходности и возврата должны располагаться на «верхнем уровне».

Итак, как вы будете выполнять итерацию с использованием подпрограмм? Вы делаете саму подпрограмму итератором, а затем «вытягиваете» результаты из основной функции:

IEnumerable<int> CountTo100Twice() { foreach (int i in CountTo100()) yield return i; foreach (int i in CountTo100()) yield return i; } IEnumerable<int> CountTo100() { for (i = 1; i <= 100; i++) { yield return i; } }

Упражнение: Рассмотрите следующий отрывок:

foreach (int i in CountTo100Twice()) { // .

}

Объясните, что происходит при 150-м (сто пятидесятом) вызове MoveNext() в приведенном выше цикле.

Рассмотрим последствия этого для рекурсивных алгоритмов (таких как обход дерева).

Теги: #csharp #перечислители #синтаксис сахара #yield #.

NET

Вместе с данным постом часто просматривают: