Python eval: difference between globals and locals

Python eval() receives two optional dictionaries: globals and locals. I was finally able to find at least two differences between them.

First difference: global variables survive until after the eval() call, local variables do not. This becomes important, if eval() returns a lambda.

globs = {"a": 42 }
locs = {"b": 10 }
print(eval("a+b", globs, locs))       # prints 52; no visible difference between usage of a and b

f = eval("lambda: a", globs, locs)    # global variable 'a' survives the eval call and can be used in a lambda later
print(f())                            # prints 42

globs["a"] = 100                      # we can even change the value of a, and the lambda will pick it up
print(f())                            # prints 100

del globs["a"]                        # if we delete globs["a"] the lambda will stop working
print(f())                            # raises NameError: name 'a' is not defined

g = eval("lambda: b", globs, locs)    # this succeeds, but local variable 'b' will not survive beyond the eval call
print(g())                            # raises NameError: name 'b' is not defined 

Second difference: local variables override global variables with the same name. This, however, is applicable only during the eval() call. If eval() returns a lambda, the global variable will be used when the lambda is invoked.

globs = {"a": 42 }
locs = {"a": 10 }
data = eval("(a, lambda: a)", globs, locs) # returns a tuple of a value and a lambda
print(data[0], data[1]())                  # prints "10 42"; lambda returns the value of the global variable

I could not find information about any other differences in the documentation or elsewhere on the Internet, and even those above I found through experiment. So, I am documenting them here for posterity.

2 Comments


  1. This is quite cool IMHO!

    Reply

Leave a Reply

Your email address will not be published. Required fields are marked *