如果没有命中,并且缓存没满,那么直接将新节点添加到双向循环链表的结尾(root[PREV],这里我认为是结尾,但是代码注释中写的是开头)(89~96 行)
最后给 wrapper 添加两个属性函数 cache_info 和 cache_clear,cache_info 显示当前缓存的命中情况的统计数据,cache_clear 用于清空缓存。对于上面阶乘相关的代码,如果在最后执行 factorial.cache_info(),会输出
CacheInfo(hits=1, misses=5, maxsize=128, currsize=5)第一次执行 factorial(5) 的时候都没命中,所以 misses = 5,第二次执行 factorial(3) 的时候,缓存命中,所以 hits = 1。
最后需要说明的是,对于有多个关键字参数的函数,如果两次调用函数关键字参数传入的顺序不同,会被认为是不同的调用,不会命中缓存。另外,被 lru_cache 装饰的函数不能包含可变类型参数如 list,因为它们不支持 hash。
总结一下,这篇文章首先简介了一下缓存的概念,然后展示了在 Python 中 lru_cache 的使用方法,最后通过源码分析了 Python 中 lru_cache 的实现细节。