Вы хотите сделать два независимых прохода по одному и тому же результату фильтрации: например, посчитать sum(valid) и затем max(valid) без пересоздания источника. Какой подход чаще всего проще и надёжнее?
AОставить generator и выполнить
sum(valid) и max(valid) подряд — generator сам переиспользуется.BПеред каждым проходом вызывать
iter(valid) — это «перемотает» generator.CСначала вызвать
next(valid) до конца, чтобы «подготовить» данные для второго прохода.DМатериализовать результат в список один раз, например
valid_list = [x for x in xs if ...], и уже по нему считать метрики.Правильный ответ. Если нужен повторный проход без пересоздания источника, материализуйте данные; генератор одноразовый.
Разбор
Generator expression и iterator в целом потребляются при первом проходе. Поэтому второй агрегат (например, max(valid)) увидит уже пустой поток. Если данные не слишком большие и вам нужен повторный доступ, проще один раз создать список и затем выполнять сколько угодно проходов. Альтернатива — каждый раз заново создавать генератор/итератор из исходного iterable.
Проверь себя · 1/3разбор после ответа
Есть
xs = [1, 2, 3] и it = iter(xs). Сначала выполняется a = list(it), а затем b = list(it). Чему равно b?Ещё вопросы по теме «Итераторы и генераторы»
- Есть `xs = [1, 2, 3]` и `it = iter(xs)`. Сначала выполняется `a = list(it)`, а затем `b = list(it)`. Чему равно `b`?
- Есть `it = iter(['a', 'b'])`. Что вернёт вызов `next(it)`?
- Дан генератор: `def gen(): print('A'); yield 1; print('B'); yield 2`. Сразу после `g = gen()` что будет выведено в консоль?
- Что создаёт выражение `squares = (x * x for x in xs)`?
- В отладке вы сделали `pairs = zip(users, spends)`, затем `debug = list(pairs)`. После этого `d = dict(pairs)` оказался пустым. Почему?
- Все вопросы по «Итераторы и генераторы» →