namespaces in eval(): spot error in 3 line program

P

pasa

I'm an old time python user, but just got bitten by namespaces in eval.
If this is an old discussion somewhere, feel free to point me there.

Based on the documentation, I would have expected the following to
work:

def foo(k): print k; print a

ns = {'a':1, 'foo': foo}
eval('foo(2)', ns)

But it does not, complete session:

[harri@labsdevgrid1 ~]$ python
Python 2.4 (#2, Feb 13 2005, 22:08:03)
[GCC 3.4.3 (Mandrakelinux 10.1 3.4.3-3mdk)] on linux2
Type "help", "copyright", "credits" or "license" for more information.2
Traceback (most recent call last):
File "<stdin>", line 1, in ?
File "<string>", line 0, in ?

huh? I'd almost be tempted to call this a bug?

Playing with locals() and globals() I see that this one works,
which I would not have expected to work:

def foo(k): print k; print ns['a']

ns = {'a':1, 'foo': foo}
eval('foo(2)', ns)

Prints out
2
1

Do functions carry their own pointer to global namespace,
which gets defined at function compile time, or what is
happening here?

-Harri
 
J

Just

"pasa said:
I'm an old time python user, but just got bitten by namespaces in eval.
If this is an old discussion somewhere, feel free to point me there.

Based on the documentation, I would have expected the following to
work:

def foo(k): print k; print a

ns = {'a':1, 'foo': foo}
eval('foo(2)', ns)

But it does not, complete session:

[harri@labsdevgrid1 ~]$ python
Python 2.4 (#2, Feb 13 2005, 22:08:03)
[GCC 3.4.3 (Mandrakelinux 10.1 3.4.3-3mdk)] on linux2
Type "help", "copyright", "credits" or "license" for more information.2
Traceback (most recent call last):
File "<stdin>", line 1, in ?
File "<string>", line 0, in ?

huh? I'd almost be tempted to call this a bug?

Playing with locals() and globals() I see that this one works,
which I would not have expected to work:

def foo(k): print k; print ns['a']

ns = {'a':1, 'foo': foo}
eval('foo(2)', ns)

Prints out
2
1

Do functions carry their own pointer to global namespace,
which gets defined at function compile time, or what is
happening here?

Function definition time. Your code is more or less equivalent to:

# A.py:
def foo(k): print k; print a

# B.py:
from A import foo
a = 1
foo()

That will fail with a NameError just the same.

Just
 
T

Terry Reedy

pasa said:
Do functions carry their own pointer to global namespace,
which gets defined at function compile time, or what is
happening here?

To expand on Just's answer:

For lexical scoping -- resolution of globals in the definition context --
some reference to that context is required. The alternative of dynamic
scoping -- resolution of globals in the calling context -- has been tried
in other languages and found wanting. For instance, if you call a function
in the math module that uses pi, sin, or cos, one almost certainly wants it
to use the object defined and bound to pi, sin, or cos in the math module.
That happens automatically with lexical scoping. With dynamic scoping, one
would have to do 'from math import *' first. And so on for everything
else.

Terry J. Reedy
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,579
Members
45,053
Latest member
BrodieSola

Latest Threads

Top