自定义一个cache函数,实现过期清除key的功能(python实现)

自定义一个cache函数,实现过期清除key的功能(5秒)

import inspect
from functools import wraps
import  time
import datetime

def cache(fn):
     local_cache = {} # 对不同函数名是不同的cache
     @wraps(fn)
     def wrapper(*args, **kwargs):
         def _clear_expire():
             # 清除缓存:注意:在对字典迭代的时候,是不能删除的!
             expire_keys = []
             # for k, v  in local_cache.items(): # {(('x', 4), ('y', 5)): (9, 1535638337.355427)}
             #     ret, stamp = v
             # 等价
             for k,(_,stamp) in local_cache.items():
                 if datetime.datetime.now().timestamp() - stamp > 5:
                     expire_keys.append(k)
             for k in expire_keys:
                 local_cache.pop(k)
             # 每次都要遍历,最好用线程,用的时候清除
         def _make_key(args,kwargs):
             sig = inspect.signature(fn)  # 获取签名 (x=4, y=5)
             params = sig.parameters  # 获取参数字典,有序的 OrderedDict([('x', ), ('y', )])
             values = list(params.values())  # 有序的 [, ]
             keys = list(params.keys())  # ['x', 'y']
             param_dic = {}  # c参数字典
             # 位置传参
             for k, v in enumerate(args):
                 param_dic[keys[k]] = v
             param_dic.update(zip(params.keys(), args))  # 二元组,放到字典中,形成 k-v对
             # 关键字传参
             param_dic.update(kwargs)  # 关键字参数,放到字典中
             # 缺省值
             for k, v in params.items():  # OrderedDict([('x', ), ('y', )])
                 if k not in param_dic:
                     param_dic[k] = v.default
             key = tuple(sorted(param_dic.items()))  # sorted生成列表,不能做key,所以tuple一下(key必须是可hash的,因为要用字典) (('x', 4), ('y', 5))
             return key

         _clear_expire()

         key = _make_key(args,kwargs)

         if key not in local_cache.keys():
             local_cache[key] = fn(*args, **kwargs), datetime.datetime.now().timestamp() # 放到二元组中,记录的是缓存的时间
             # 形成一个 {key:stamp}的字典
             #如果说到点清除,最好写结束时间,到点清除,记录一个未来时间

         print(local_cache) # {(('x', 4), ('y', 5)): (9, 1535638337.355427)}
         # print(local_cache[key])
         return local_cache[key]

     return wrapper

@cache
def add(x,y):
    return x+y

add(4,5)
time.sleep(5)
add(4,y=5)
time.sleep(5)
add(x=4,y=5)

你可能感兴趣的:(python基础)