Выбор ответа Senior GC, IDisposable и производительность обновлено

Где выделит память лямбда в цикле

Вопрос

Метод в горячем цикле вызывает items.Where(x => x.Price > limit).Count(), где limit это параметр метода. Какие аллокации происходят на каждый вызов метода?

Попробуйте сами

Выберите вариант, и откроется разбор.

Показать ответ и разбор

Коротко

Правильный ответ: Замыкание для limit, делегат и итератор. Лямбда захватывает limit, поэтому компилятор создаёт объект-замыкание и новый делегат при каждом вызове метода (кешируются только лямбды без захвата).

Варианты ответа

  1. Никаких: LINQ полностью работает на стеке
  2. Замыкание для limit, делегат и итераторправильный ответ
  3. Только итератор Where: делегат кешируется всегда
  4. Копия всей коллекции items перед фильтрацией

Разбор

Лямбда захватывает limit, поэтому компилятор создаёт объект-замыкание и новый делегат при каждом вызове метода (кешируются только лямбды без захвата). Where создаёт объект-итератор. Коллекция не копируется. В горячем коде это заменяют на цикл foreach с условием или на Count(predicate) без промежуточного Where, хотя замыкание при этом остаётся.

Ответьте сами, а не прочитайте

В тренажёре вопрос попадёт в повторения и вернётся, когда начнёт забываться. Плюс билеты с зачётом: 20 вопросов, не больше 2 ошибок.