functools.lru_cache
メモリをリークせずにクラス内で使用するにはどうすればよいですか?
次の最小限の例ではfoo
、スコープ外になり、リファラー ( 以外lru_cache
) がないにもかかわらず、インスタンスは解放されません。
from functools import lru_cache
class BigClass:
pass
class Foo:
def __init__(self):
self.big = BigClass()
@lru_cache(maxsize=16)
def cached_method(self, x):
return x + 5
def fun():
foo = Foo()
print(foo.cached_method(10))
print(foo.cached_method(10)) # use cache
return 'something'
fun()
しかしfoo
、したがってfoo.big
(a BigClass
) はまだ生きている
import gc; gc.collect() # collect garbage
len([obj for obj in gc.get_objects() if isinstance(obj, Foo)]) # is 1
つまり、Foo
/BigClass
インスタンスはまだメモリ内に存在します。削除してもFoo
( del Foo
)、それらは解放されません。
なぜlru_cache
インスタンスを保持しているのですか? キャッシュは実際のオブジェクトではなくハッシュを使用していませんか?
lru_cache
クラス内で s を使用する推奨される方法は何ですか?
私は 2 つの回避策を知っています: インスタンスごとのキャッシュを使用するか、キャッシュがオブジェクトを無視するようにします(ただし、間違った結果につながる可能性があります)。