Повреждение урожая, эквивалентное возврату Счетного <T>.Empty из метода, возвращаясь IEnumerable <T>

Эти два метода, кажется, ведут себя то же мне

public IEnumerable<string> GetNothing()
{
    return Enumerable.Empty<string>();
}

public IEnumerable<string> GetLessThanNothing()
{
    yield break;
}

Я представил каждого в сценариях тестирования, и я не вижу значимого различия в скорости, но yield break версия немного быстрее.

Там какие-либо причины состоят в том, чтобы использовать один по другому? Каждого легче считать, чем другой? Существует ли различие в поведении, которое имело бы значение для вызывающей стороны?

39
задан Mike Two 16 March 2010 в 18:58
поделиться

3 ответа

Если вы намерены всегда возвращать пустое суммируемое, то использование синтаксиса Enumerable.Empty() является более декларативным IMHO.

Разница в производительности здесь почти наверняка не существенна. Я бы сосредоточился на читабельности, а не на производительности здесь, пока профайлировщик не показал вам, что это проблема.

36
ответ дан 27 November 2019 в 02:40
поделиться

Кажется, что yield break инстанцирует по крайней мере на один объект меньше, чем return Enumerable.Empty(). Кроме того, могут быть некоторые проверки, которые вы замыкаете с помощью yield break. И если ничего другого нет, то это на одну обертку функции меньше, через которую проходит ваш стек, что было бы заметно, хотя и не заметно.

Однако, я согласен с другим ответом, опубликованным на сайте, что .Empty является "предпочтительным" способом сделать это.

1
ответ дан 27 November 2019 в 02:40
поделиться

Методы IEnumerable с yield break или yield return в теле преобразуются в машины состояний. В таких методах нельзя смешивать возвраты yield с традиционными возвратами. Я имею в виду, что если вы возвращаете что-то в одной части метода, вы не можете вернуть ICollection в другой.

С другой стороны, предположим, что вы реализуете метод с типом возврата IEnumerable, добавляя элементы в коллекцию, а затем возвращая копию коллекции, доступную только для чтения. Если по какой-то причине вы хотите просто вернуть пустую коллекцию, вы не можете сделать yield break. Все, что вы можете сделать, это просто вернуть Enumerable.Empty().

Если вы профилировали оба способа, и нет никаких существенных изменений, то можете просто забыть об этом :)

.
14
ответ дан 27 November 2019 в 02:40
поделиться
Другие вопросы по тегам:

Похожие вопросы: