итерация бесконечного генератора до выполнения условия - PullRequest
0 голосов
/ 26 апреля 2018

У меня небольшие проблемы с пониманием генераторов на python. Допустим, у меня есть следующий простой генератор:

def test_gen():
    yield 1
    yield 2
    yield 5
    yield 8
    yield 12

Это просто даст несколько цифр. Допустим, я хочу сохранить печать значений из генератора, пока значение не станет больше 10. Моя первая попытка была просто

gen = test_gen()
for i in gen:
    while i > 10:
        print(i)

Но это просто печатает 1 навсегда. Я обнаружил, что делает

gen = test_gen()
for i in gen:
    if i > 10:
        print(i)

работает, как и ожидалось, потому что он просто перебирает каждое значение в генераторе, пока StopIteration не будет повышен. Затем я столкнулся с проблемой бесконечного генератора, такого как этот, который генерирует простые числа:

def prime_gen():
    D = dict()
    n = 2
    while True:
        if n not in D:
            yield n
            D[n*n] = [n]
        else:
            for p in D[n]:
                D.setdefault(p + n, []).append(p)
            del D[n]
        n += 1

Тогда, если я сделаю что-то вроде

primes = prime_gen()
for p in primes:
    if p < 100:
        print(p)

тогда он напечатает все до p, но затем повесит трубку. Я думаю, что это зависает, потому что он пытается проверить все значения, которые генерирует primes, что происходит вечно. Как правильно перебирать бесконечный генератор до тех пор, пока не будет выполнено такое условие? Единственный способ, который я нашел, это делать

primes = prime_gen()
for p in primes:
    if p < 100:
        print(p)
    else:
        break

но я чувствую, что есть более питонический способ сделать это.

Ответы [ 2 ]

0 голосов
/ 26 апреля 2018

Ваш break метод довольно Pythonic, но я бы подумал обернуть генератор:

for p in (i if i < 100 else StopIteration for i in primes):
    print(p)
0 голосов
/ 26 апреля 2018

itertools.takewhile()

for i in itertools.takewhile(lambda x: x < 100, primes):
  print i
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...