Есть ли в питоне такая вещь, как "слишком много операторов yield"? - PullRequest
4 голосов
/ 25 февраля 2010

Если сделать листинг каталога и прочитать файлы внутри, в какой момент производительность yield начинает ухудшаться по сравнению с возвратом списка всех файлов в каталоге?

Здесь я предполагаю, что у одного достаточно ОЗУ для возврата (потенциально огромного) списка.

PS У меня проблемы с встраиванием кода в комментарий, поэтому я приведу здесь несколько примеров.

def list_dirs_list():
    # list version
    return glob.glob(/some/path/*)

def list_dirs_iter():
    # iterator version
    return glob.iglob(/some/path/*)

За кулисами оба вызова glob используют os.listdir, поэтому кажется, что они эквивалентны по производительности. Но этот документ на Python , кажется, подразумевает, что glob.iglob быстрее.

Ответы [ 4 ]

5 голосов
/ 25 февраля 2010

Нет смысла, когда дальнейшее использование yield приводит к снижению производительности. Фактически, по сравнению со сборкой объектов в списке, yield на самом деле улучшается при сравнении, чем больше элементов.

2 голосов
/ 25 февраля 2010

Это зависит от того, как вы делаете список каталогов. Большинство механизмов в Python вытягивают весь список каталогов в список; если делать это таким образом, то даже один выход - пустая трата времени. Если используется opendir(3), то это, вероятно, случайное число, согласно определению XKCD «случайный».

1 голос
/ 25 февраля 2010

использование yield по функциональности аналогично написанию класса функтора, даже с точки зрения реализации или производительности, за исключением того, что он, вероятно, может вызвать генератор немного быстрее, чем метод __call__ в самодельном классе, потому что это встроен в реализацию генератора C.

Чтобы забить этот дом, использование и грубая реализация следующего одинаковы:

def generator_counter():
    i = 0
    while True:
        i += 1
        yield i

class functor_counter():
    def __init__(self):
        self.i = 0
    def __call__(self):
        i += 1
        return i
0 голосов
/ 22 мая 2011

В Python 2.7 определение glob равно

def glob(pathname): return list(iglob(pathname))

Так что, по крайней мере, для этой версии glob никогда не может быть быстрее, чем iglob.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...