2011-12-07 99 views
0

我想覆盖全局变量,以便任何不存在的属性名称 返回自身(名称字符串)。 其原因是在eval中使用它来做一些快速/ hacky的c initilizer列表解析,(当然,正因为如此)。 我的代码:覆盖与__getattr__问题的eval全局变量

class EvalGlobalsDict(dict): 
    def __getattr__(self, name): 
     if hasattr(self, name): 
      return super(EvalGlobalsDict, self).__getattr__(name) 
     else: 
      return name 


eval_globals = EvalGlobalsDict(globals()) 

每当我试着EVAL它给了我一个NameError

eval("aaa",eval_globals) 

如果我尝试直接调用

eval("globals().__getattr__("dir")",eval_globals) 
eval("globals().__getattr__("dir")",eval_globals) 

我只得到一个不存在的名字attr名称字符串,即使是有效的attributtes。 我在做什么错?

+2

通过AKX给出的答案是正确的,但仅供参考'__getattr__'只被调用,如果常规属性查找失败,所以你不需要'if' /'else' - 只要'返回名称'就可以做到这一点(如果它实际上是你想修改的属性访问)。 – agf

回答

4

由于您正在继承字典,因此您需要覆盖__getitem__(索引访问器)。

class EvalGlobalsDict(dict): 
    def __getitem__(self, name): 
     return self.get(name, name) 

foo = 1337 
eval_globals = EvalGlobalsDict(globals()) 
print repr(eval("aaa", eval_globals)) 
print repr(eval("foo", eval_globals)) 

打印

> 'aaa' 
> 1337