5

リスト内包表記として実行すると、問題なく実行されることがあります。

それは、

[myClass().Function(things) for things in biggerThing]

Functionはメソッドであり、リストを作成します。メソッド自体は何も返しませんが、リストは内部で操作されます。

これをgeneratorに変更すると、

(myClass().Function(things) for things in biggerThing)

私が期待するようにデータを操作しません。実際、それをまったく操作していないようです。

リスト内包表記とジェネレーターの機能上の違いは何ですか?

4

5 に答える 5

5

ジェネレーターは、消費されるとオンザフライで評価されます。したがって、ジェネレーターを反復処理しない場合、その要素は評価されません。

したがって、あなたがした場合:

for _ in (myClass().Function(things) for things in biggerThing):
    pass

Function実行されます。


ここで、あなたの意図は本当に明確ではありません。

代わりに、次の使用を検討してmapください。

map(myClass().Function, biggerThing)  

これは常に MyClass の同じインスタンスを使用することに注意してください

それが問題である場合は、次のようにします。

for things in BiggerThing:
    myClass().Function(things)
于 2013-11-12T15:54:23.130 に答える
3

ジェネレーターは遅延評価されます。関数を評価するには、ジェネレーターを処理する必要があります。collections.dequeジェネレーターを消費するために使用できます。

import collections
generator = (myClass().Function(thing) for thing in biggerThing) 
collections.deque(generator , maxlen=0)

または の使用を検討する@staticmethod@classmethod、またはに変更します

myfunc = myClass().Function
generator = (myfunc(thing) for thing in biggerThing) 
collections.deque(generator , maxlen=0)

myClass処理ごとに作成の新しいインスタンスを減らすためthing

更新、パフォーマンス

  1. collectionsiteration
デフ l():
    範囲内の x の場合 (100):
       y = x**2
      利回りy

デフ消費(それ):
    その中の私のために:
        合格

>>> timeit.timeit('from __main__ import l, consumer; consumer(l())', number=10000)
0.4535369873046875
>>> timeit.timeit('from __main__ import l, collections; collections.deque(l(), 0)', number=10000)
0.24533605575561523
  1. インスタンス vs クラス vs 静的メソッド
クラステスト(オブジェクト):
    @静的メソッド
    デフ stat_pow(x):
        x**2 を返す
    @クラスメソッド
    def class_pow(cls, x):
        x**2 を返す
    def inst_pow(自己、x):
        x**2 を返す

def static_gen():
    範囲内の x の場合 (100):
        yield Test.stat_pow(x)

def class_gen():
    範囲内の x の場合 (100):
        yield Test.class_pow(x)

デフ inst_gen():
    範囲内の x の場合 (100):
        yield Test().inst_pow(x)

>>> timeit.timeit('from __main__ import static_gen as f, collections; collections.deque(f(), 0)', number=10000)
0.5983021259307861
>>> timeit.timeit('from __main__ import class_gen as f, collections; collections.deque(f(), 0)', number=10000)
0.6772890090942383
>>> timeit.timeit('from __main__ import inst_gen as f, collections; collections.deque(f(), 0)', number=10000)
0.8273470401763916
于 2013-11-12T15:56:57.193 に答える
2

ジェネレーターを作成すると、各要素は 1 回しか使用できません。食べながらクッキーのバッチを作成しているようなものです。それらは目的を果たします(私を幸せにしてくれます)が、一度使用すると消えてしまいます。

リスト内包表記はリストを作成し、そのデータ構造に永遠にアクセスできるようにします (表向きは)。それらに対してすべてのリストメソッドを使用することもできます (非常に便利です)。しかし、アイデアは、実際のデータ構造(データを保持するもの) を作成することです。

こちらの記事をご覧ください:ジェネレーターとリスト内包表記

于 2013-11-12T15:56:33.687 に答える