我正在尝试将数据类,属性和lru_caches结合起来以用于一些计算科学代码:
from dataclasses import dataclass
from typing import Any
from functools import lru_cache
@dataclass
class F:
a: Any = 1
b: Any = 2
c: Any = 3
@property
@lru_cache(1)
def d(self):
print('Computing d')
return (self.a+self.b)**self.c
f=F()
print(f.d)
print(f.d)
我希望看到
Computing d
27
27
但是得到
TypeError: unhashable type: 'F'
有没有办法解决这个问题?
答案 0 :(得分:2)
lru_cache
就像备忘录一样,因此它哈希传递给函数的参数并存储结果。您的课程不可散列。要使其可散列,请添加如下内容
class F:
....
def __hash__(self):
return hash((self.a, self.b, self.c))
之所以这样做,是因为这3个属性使每个实例“唯一”-我们无需对方法进行哈希处理,因为所有实例都具有相同的方法。
在大多数普通类中,除非找到__dict__
方法,否则它将__hash__
用于常规哈希。数据类文档解释说,数据类可能会生成哈希方法,但这取决于您如何设置数据类,因为默认情况下该对象被认为是可变的(并且可变对象(如列表)不能被哈希)。
数据类文档指出,如果在用eq
装饰时将参数frozen
和True
设置为@dataclass()
,则会生成一个散列方法,但是您的应用程序可能不会frozen
禁止在实例上分配属性。
https://docs.python.org/3/library/dataclasses.html#dataclasses.dataclass