访问Python 2.6中的外部作用域

kol*_*pto 7 python scope

比方说,我有一些变量范围,并且在这个范围内调用的函数想要更改一些不可变变量:

def outer():
    s = 'qwerty'
    n = 123
    modify()

def modify():
    s = 'abcd'
    n = 456

有可能以某种方式访问​​外部范围?类似nonlocalPy3k的变量.

当然我可以s,n = modify(s,n)在这种情况下做,但是如果我需要一些在那里执行的通用"注入"并且必须能够重新分配给任意变量呢?

我有性能,所以,如果可能的话,eval不欢迎堆栈框架检查:)


UPD:这是不可能的.期.但是,如何访问外部作用域中的变量有一些选项:

  1. 使用全局变量.顺便说一句,func.__globals__是一个可变的字典;)
  2. 将变量存储在dict/class-instance /任何其他可变容器中
  3. 将变量作为参数提供并将其作为元组返回: a,b,c = innerfunc(a,b,c)
  4. 注入其他函数的字节码.这可以通过byteplaypython模块实现.

orl*_*rlp 7

定义函数之外的变量并使用global关键字.

s, n = "", 0

def outer():
    global n, s
    n = 123
    s = 'qwerty'
    modify()

def modify():
    global n, s
    s = 'abcd'
    n = 456
Run Code Online (Sandbox Code Playgroud)


joe*_*ker 7

有时我遇到这样的代码.嵌套函数修改可变对象而不是分配给nonlocal:

def outer():
    s = [4]
    def inner():
        s[0] = 5
    inner()
Run Code Online (Sandbox Code Playgroud)

  • 您可以键入outer.s = 4,但这将为outer()函数指定一个属性.它与分配给名为s的局部变量不同. (3认同)

小智 3

不是工作原理nonlocal。它不提供动态范围(这只是一个巨大的 PITA 等待发生,甚至比一般的“邪恶”功能更有用)。它只是修复了词法范围。

无论如何,你不能做你想做的事(我会说这是一件好事)。甚至没有肮脏但简单的黑客攻击(当我们这样做时:我们不会阻止这样的黑客攻击,因为它们通常表现得更差一些!)。忘记它并正确解决真正的问题(你没有说出它的名字,所以我们对此无话可说)。

您可以获得的最接近的是定义一些对象,该对象包含您想要共享的所有内容并显式传递它(例如,创建一个类并使用self,如另一个答案中所建议的)。但这在任何地方都相对麻烦,而且仍然是黑客行为(尽管比动态作用域更好,因为“显式优于隐式”)。