День восемьдесят девятый. #ЗаметкиНаПолях

Выражение yield return. Примеры использования

1. Кастомные итерации

Допустим, у нас есть список чисел. Мы хотим отобразить все числа, которые больше определённого числа. Обычно нам пришлось бы:

- создать временный список,

- в цикле пройти по исходному списку, сохраняя во временный список подходящие значения,

- пройти по временному списку, чтобы использовать полученные значения.

Мы можем избежать лишней работы, используя yield return:

IEnumerable<int> GetNumbersGreaterThan3(List<int> numbers) 

{

foreach(var nr in numbers)

{

if(nr > 3)

yield return nr;

}

}

foreach(var nr in GetNumbersGreaterThan3(new List<int> {1,2,3,4,5})

Console.WriteLine(nr);

Здесь выполнение кода совершенно другое. Исходный список перебирается всего один раз, и только нужные значения выдаются методом-итератором вызывающему коду (в этом случае циклу foreach).



2. Итерации с сохранением состояния

Метод-итератор, содержащий yield return, сохраняет не только позицию после выдачи очередного значения, но и своё состояние:

IEnumerable<int> Totals(List<int> numbers)

{

var total = 0;

foreach(var number in numbers)

{

total += number;

yield return total;

}

}

foreach(var total in Totals(new List<int> {1,2,3,4,5})

Console.WriteLine(total);

Этот код вернёт значения 1,3,6,10,15. Поскольку состояние сохраняется, переменная total будет сохранять значения между итерациями, тем самым подсчитывая промежуточную сумму чисел списка.



3. Асинхронные потоки

В C# 8 появилась возможность создавать асинхронные потоки, которые были описаны в этом посте: https://t.me/NetDeveloperDiary/88



Источники:

-
https://docs.microsoft.com/ru-ru/dotnet/csharp/language-reference/keywords/yield

-
https://www.kenneth-truyers.net/2016/05/12/yield-return-in-c/



Продолжение следует…