globals( ) and binding doubt (newbie) !

Steve Holden sholden at holdenweb.com
Tue Jan 8 10:21:55 EST 2002


"Karthik Gurumurthy" <karthikg at aztec.soft.net> wrote in message
news:mailman.1010502130.4654.python-list at python.org...
>
> hi all,
>
> please take a look at python session dump: I have put comments at
> significant places.
>
> >>> def f1():
> ...     print 'f1'
> ...
> >>> def f2():
> ...     print 'f2'
> ...
> >>> def f3():
> ...     print 'f3'
> ...
> >>> l = [f1,f2,f3]
> >>> map(lambda f:f(),l)
> f1
> f2
> f3
> [None, None, None]
> >>> def f1(a):
> ...     print a
> ...
> >>> def f2(a):
> ...     print a
> ...
> >>> def f3(a):
> ...     print a
> ...
> >>>
> >>>
> >>> seq = [f1,f2,f3] ##### Here seq is filled with f1,f2 and f3
> >>>
> >>> l = [1,2,3,4,5]
> >>> map(lambda i:map(lambda f:f(i),seq),l)
> 1
> 1
> 1
> 2
> 2
> 2
> 3
> 3
> 3
> 4
> 4
> 4
> 5
> 5
> 5
> [[None, None, None], [None, None, None], [None, None, None], [None, None,
> None], [None, No
> ne, None]]
> >>> def f1(a): ##### changed the implementations of the functions
> ...     print "f1 " + str(a) ##### now globals would have bound the names
> f1,f2 and f3 to the latest definitions
> ...
> >>> def f2(b):
> ...     print "f2 " + str(b)
> ...
> >>> def f3(c):
> ...     print "f3 " + str(c)
> ...
> >>> map(lambda i:map(lambda f:f(i),seq),l) ##### But this seems to have
made
> the call on the earlier definition

Correct. That's because you created a seq that referred to the original
functions. Just because you have now bound their names to different
functions that doesn't stop them existing. In point of fact the original
function definitions can't be garbage-collected precisely because the seq
list contains a reference to each of the three.

> 1 ##### seq is the list which the methods
> 1 ##### did'nt work as expected
> 1
> 2
> 2
> 2
> 3
> 3
> 3
> 4
> 4
> 4
> 5
> 5
> 5
> [[None, None, None], [None, None, None], [None, None, None], [None, None,
> None], [None, No
> ne, None]]
> >>> seq
> [<function f1 at 0x00780CE0>, <function f2 at 0x007817A0>, <function f3 at

> 0x00781150>]

And this very clearly shows you exactly what's happening: the first element
of seq is bound to the original function, while f1 is now bound to your
second definition!

It's a little confusing, because the type information attempts to help by
including the name to which the function definition was originally bound,
making it look as though your program has two "f1" functions. In fact this
is because they were both bound (by a def statement) to the same name when
they were defined.

> >>> globals()
> {'test1': <module 'test1' from 'test1.py'>, 'f1': <function f1 at
> 0x00786350>, 'f2': <func
> tion f2 at 0x007839E0>, 'f3': <function f3 at 0x00780C70>, 'seq':
[<function
> f1 at 0x00780
> CE0>, <function f2 at 0x007817A0>, <function f3 at 0x00781150>],
> '__builtins__': <module '
> __builtin__' (built-in)>, '__name__': '__main__', '__doc__': None, 'l':
[1,
> 2, 3, 4, 5]}
> >>>
> >>>
> >>>
> >>> seq = [f1,f2,f3]     ##### I had to re-initialize the list with the
> same names again.
> >>> map(lambda i:map(lambda f:f(i),seq),l)
> f1 1 ##### Then things worked fine
> f2 1
> f3 1
> f1 2
> f2 2
> f3 2
> f1 3
> f2 3
> f3 3
> f1 4
> f2 4
> f3 4
> f1 5
> f2 5
> f3 5
> [[None, None, None], [None, None, None], [None, None, None], [None, None,
> None], [None, No
> ne, None]]
> >>>
>
Exactly as you would expect.

> Can someone tell me why it did'nt use the correct versions of the
functions
> earlier.
> When python comes across a name, it does look up in locals() or globals()
> and then executes the
> one mapped there?
>
Yes, at a first approximation. But your code isn't using names, it's using
function references stored in a list before the names were rebound.

> When i redefined f1 , f2 and f3, globals would have accepted these and
> overwritten the earlier one?
>
>
They did overwrite the earlier ones, but that didn't change the bindings of
the elements of seq - that change only took place with your second
assignment to seq.

> thanks for your patience!

Hope this clarifies things for you.

regards
 Steve
--
http://www.holdenweb.com/








More information about the Python-list mailing list