次のリスト内包表記を使用しています。
resources = [obj.get("file") for obj in iterator if obj.get("file") != None]
if ステートメントでチェックされたときの値を「キャッシュ」して、戻りリストを生成するときに obj を再度obj.get("file")
呼び出す必要がないようにする方法はありますか?get
次のリスト内包表記を使用しています。
resources = [obj.get("file") for obj in iterator if obj.get("file") != None]
if ステートメントでチェックされたときの値を「キャッシュ」して、戻りリストを生成するときに obj を再度obj.get("file")
呼び出す必要がないようにする方法はありますか?get
resources = filter(None, (obj.get("file") for obj in iterator))
独自の評価関数を提供する方法については、 filterのドキュメントを参照してください。None
(上記のように) 関数を渡すと、true でないすべての値が除外されます。
obj.get() が奇妙なメソッドを持つオブジェクトを返す場合、元のコードとまったく同じ結果を得るため__nonzero__
に渡す必要があります。lambda obj: obj != None
使用する代わりにリスト/イテレータの内包表記を使用したい場合は、次のようにfilter
単純に使用できます。
resources = [file_obj
for file_obj in (obj.get("file") for obj in iterator)
if file_obj is not None]
値を保持するための一時的なdictを作成します。次に、このdictをキャッシュとして使用する関数を作成し、次のようにリスト内包表記でその関数を使用します。
obj_cache = {}
def cache_get (target, key):
if (target, key) not in obj_cache: obj_cache[(target, key)] = target.get(key)
return obj_cache[(target, key)]
resources = [cache_get(obj, "file") for obj in iterator if cache_get(obj, "file") != None]
また、おそらくこれはすでに知っているでしょう(もしそうなら、この答えは無視してください)が、obj.get( "file")がデータベース呼び出しを行ったり、ファイルを開いたり、ネットワーク経由でリクエストを行ったり、その他の可能性がある場合を除きます。コストにO(n)を追加するだけなので、コストが高く、反復ごとに1回ではなく2回呼び出すことはおそらく無害です。
次のようなことを試してください:
resources = filter( lambda x: x is not None, [obj.get("file") for ob jin iterator])