Python:静态变量装饰器
发布时间:2020-12-20 13:03:36 所属栏目:Python 来源:网络整理
导读:我想创建一个像下面这样的装饰器,但我似乎无法想到一个有效的实现.我开始认为这是不可能的,但我想我先问你们. 我意识到在Python中有各种其他方法可以创建静态变量,但我发现这些方法很难看.如果可能的话,我真的想使用下面的语法. @static(x=0)def f(): x += 1
我想创建一个像下面这样的装饰器,但我似乎无法想到一个有效的实现.我开始认为这是不可能的,但我想我先问你们.
我意识到在Python中有各种其他方法可以创建静态变量,但我发现这些方法很难看.如果可能的话,我真的想使用下面的语法. @static(x=0) def f(): x += 1 print x f() #prints 1 f() #prints 2 我不关心静态的实现是长期还是黑客,只要它像上面那样工作. 我创建了这个版本,但它只允许< function>.< varname>语法,使用更长的函数和变量名称很快就会变得很麻烦. def static(**assignments): def decorate(func): for var,val in assignments.items(): setattr(func,var,val) return func return decorate 我想到的各种事情,但无法开展工作的是: >将f(装饰函数)更改为可调用类,并以某种方式透明地将静态变量存储在自身中. 解决方法
这是一个似乎有用的装饰器.
请注意,这需要在函数末尾返回locals(),因为无法从外部设置本地(我没有太多编程经验,所以如果有办法,我不知道). class Static(object): def __init__(self,**kwargs): self.kwargs = kwargs def __call__(self,f): def wrapped_f(): try: new_kwargs = {} for key in self.kwargs: i = getattr(f,key) new_kwargs[key] = i self.kwargs = new_kwargs except: pass for key,value in f(**self.kwargs).items(): setattr(f,key,value) return wrapped_f @Static(x=0,y=5,z='...') def f(x,y,z): x += 1 y += 5 print x,z return locals() 输出将是: >>> f() 1 10 ... >>> f() 2 15 ... >>> f() 3 20 ... 编辑: 我在http://code.activestate.com/recipes/410698/找到了一些东西,并决定尝试添加它.它现在没有回报. 再次编辑:更改为使其快几秒. def static(**kwargs): def wrap_f(function): def probeFunc(frame,event,arg): if event == 'call': frame.f_locals.update(kwargs) frame.f_globals.update(kwargs) elif event == 'return': for key in kwargs: kwargs[key] = frame.f_locals[key] sys.settrace(None) return probeFunc def traced(): sys.settrace(probeFunc) function() return traced return wrap_f 测试: @static(x=1) def f(): x += 1 global_x = 1 def test_non_static(): global global_x global_x += 1 print 'Timeit static function: %s' % timeit.timeit(f) print 'Timeit global variable: %s' % timeit.timeit(test_non_static) 输出: Timeit static function: 5.10412869535 Timeit global variable: 0.242917510783 使用settrace会大大减慢它的速度. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |