Why are both locals() and globals() set?

Steve D'Aprano steve+python at pearwood.info
Sat Dec 23 00:58:29 EST 2017


On Sat, 23 Dec 2017 03:01 pm, Peng Yu wrote:

> Hi, The following example shows that both locals() and globals() are
> updated when x and f are defined. Shouldn't they be considered and
> global variable and functions only? Why does it make sense to set
> locals() as well? Thanks.

There are three places you can call locals() and globals():

(1) Inside a function:

    def function():
        x = 1
        L = locals()
        G = globals()
        print "id(L)=%d  id(G)=%d" % (id(L), id(G))


(2) Inside a class definition:

    class Class(object):
        x = 1
        L = locals()
        G = globals()
        print "id(L)=%d  id(G)=%d" % (id(L), id(G))

(3) At the top level of a module (outside of any function or class):

    # module
    x = 1
    L = locals()
    G = globals()
    print "id(L)=%d  id(G)=%d" % (id(L), id(G))



If you try this, you will find that in #3, the dicts L and G have the same ID
number. This means that at the module level, locals() and globals() are the
same dict. This is (barely!) documented here:

https://docs.python.org/2/reference/executionmodel.html#binding-of-names

where it tells us that "The variables of the module code block are local and
global" but not documented here:

https://docs.python.org/2/library/functions.html#locals

I've raised an issue for that too: https://bugs.python.org/issue32413


Also note that for technical reasons, assigning to locals() inside a function
is not guaranteed to always work. The locals() dict returned is *sometimes* a
copy of the actual local variables, and so assigning to it does not assign to
the actual local variable. This is a tricky area of Python, where different
versions and different implementations (such as CPython, IronPython, Jython,
PyPy) may behave differently.


By the way, using globals() and locals() is considered an "advanced" feature.
If you want to set a variable, use ordinary assignment:

    # set a local
    x = 1

    # to set a global from inside a function or class, declare it global
    global x
    x = 1

rather than trying to play around with globals() and locals(). 



-- 
Steve
“Cheer up,” they said, “things could be worse.” So I cheered up, and sure
enough, things got worse.




More information about the Python-list mailing list