Mehrdad Mehrdad - 1 year ago 39
Python Question

How to bind a name statically (lexically) in Python?

Consider this code:

class Bar(object): pass

class Foo(object):
def bar(self): return Bar()

f = Foo()
def Bar(): pass

It prints
. But the poor guy
didn't expect
to be what it became afterward!

My question is, what is the "best" (most elegant, most efficient, most Pythonic, whatever) code I can write inside of
(hopefully without polluting outside scopes) that will make sure
can reference the
that was defined at the time of its declaration rather than invocation?

(It's not that I can't come up with any solutions, but rather it's that I don't know what the proper solution is.)

Answer Source

Answering my own question, but the answer is to put everything in a closure:

def static_define(locals, super, tuple):  # All arguments are bound STATICALLY
    # Anything defined here will be exported externally
    class Foo(tuple):
        def __new__(cls, *args):
            return super(Foo, cls).__new__(cls, args)
    return locals()

# The following line "exports" all the returned locals into the current global namespace
(lambda f, bi: (lambda g: g.pop(f.__name__) and bi.None or g.update((lambda args: (lambda l: bi.reduce(lambda l, v: l.pop(v, bi.None) and bi.None or l, args, l))(f(* v: bi.eval(v, g), args))))(bi.__import__('inspect').getargspec(f).args)))(f.__globals__))(static_define, __builtins__)

super = None  # tamper!
print Foo()   # unaffected by tampering