python - python 2和python 3的'functools.lru_cache'有什么变化吗?
问题描述
我的代码在这里可以正常工作,但从python 2 到 python 3python2.7
的任何更改都失败了。python 3
functools.lru_cache(maxsize=32)
我得到的错误是我的configparser
对象在缓存中functools.lru_cache
说
TypeError: unhashable type: 'ConfigParser'
想了解'functools.lru_cache'
python 2 和 python 3 的变化吗?
#CONFI FILE
[translate]
api_url = https://url
api_version = version_num
api_key = key_value
#code goes here
import functools
from configparser import ConfigParser as SafeConfigParser
config = SafeConfigParser()
path ="./conf/services.ini"
config.read(path)
@functools.lru_cache(maxsize=32)
def build_api_params_key(config):
"""Build the api url and return with key."""
api_url = config.get('translate', 'api_url')
api_version = config.get('translate', 'api_version')
api_key = config.get('translate', 'api_key')
full_api_url = api_url + api_version
return api_key
解决方案
这里的问题不是functools.lru_cache
,它实际上是 ConfigParser。ConfigParser
继承自RawConfigParser
,在 Python 3x 中,继承自collections.abc.MutableMapping
. 抽象类是不可散列的MutableMapping
,因为它是可变的并且不实现__hash__
魔术方法。
由于ConfigParser
实例不可散列,它不能用作functools.lru_cache
装饰器中缓存字典的键。
如需进一步参考,请参阅configparser 文档的这一部分。
假设需要缓存配置文件的内容,另一种选择是读取文件的内容,然后将内容字符串传递给缓存的函数,就像这样
import functools
from configparser import ConfigParser as SafeConfigParser
path = "./conf/services.ini"
config_contents = open(path).read()
@functools.lru_cache(maxsize=32)
def build_api_params_key(config_contents: str):
"""Build the api url and return with key."""
config = SafeConfigParser()
config.read_string(config_contents)
api_url = config.get('translate', 'api_url')
api_version = config.get('translate', 'api_version')
api_key = config.get('translate', 'api_key')
full_api_url = api_url + api_version
return api_key
在上面的解决方案中,读取配置文件以获取包含其内容的字符串。由于字符串是可散列的,因此可以将其传递给缓存函数。如果您希望在函数中读取文件的内容,也可以对文件指针执行类似的操作。但是,这些解决方案与read_string
未定义的 Python 2.7 不兼容。
推荐阅读
- button - JavaFX 按钮取消选择
- android - Android InputType 密码和 InputType 数字不带数字
- java - 为什么基于 Java 的模拟程序会在更快的计算机上以相同的速度运行?
- git - 如何在内联 groovy 脚本中添加 git clone 操作
- reactjs - 希望 React 忽略 style 属性
- java - 在“计算启动按钮工具提示”期间发生内部错误。java.lang.IllegalArgumentException
- php - 如何随机选择两个字符串?
- c# - 检查子类型 T 的泛型对象
- c++ - 在运行时获取可用的库函数
- .net - 如何获取变量的值
在 Infer.Net 中?