Question about math.pi is mutable

BartC bc at freeuk.com
Sun Nov 8 17:35:06 EST 2015


On 08/11/2015 21:00, Ben Finney wrote:
> BartC <bc at freeuk.com> writes:
>
>> I've never understood why this seems to be necessary in Python. Why do
>> names have to be looked up? (I'm assuming this is searching by name in
>> some sort of table.)
>
> No, it is literally looking the name up as a key in a namespace
> dictionary — which is just like any other Python dictionary, but
> nominated internally for use as the namespace dictionary.
>
> The distinction is important, because like any other dictionary it can
> change at run-time and the bindings between name and value can change,
> can be added, and can be removed.

That part is not a problem.

>> When a module is compiled, while the compiler can't see the
>> definitions inside the imported modules, it /will/ know all the names
>> that appear in this module, so it can organise them into fixed tables.
>
> Not true. The namespace can change dynamically, which is another way of
> what people have been trying to tell you all through this thread.
>
> The compiler *cannot* know what the names will be at every single point
> they'll be looked un in the namespace dictionary. This dynamism of each
> namespace is a Python feature.

Suppose this is the python program:

import m
a=10
b=20
c=30
m.f()

The set of global names the compiler knows will be ("m","a","b","c").

I don't believe code can remove these names (that would cause problems). 
You say the set of global names can be added to - after this lot, but I 
can't see that the first four are going to change.

Therefore these names could be referred to by index.

Attributes are harder because they are more of a free-for-all, but 
suppose you do have m.f().

"m" is easy, it's entry 0 in the global table for this module, so no 
lookup-by-name is needed. You examine it, and it's a module.

It's now necessary to find f within the global table for m. This is 
where it gets tricky if you want to avoid a lookup. And I expect you 
will say that any code can randomly add names within the global table of m.

But bear with me. Suppose the interpreter were to maintain a table for 
each static (not runtime) attribute encountered in the source code. The 
compile can produce empty tables for the attributes it's seen. In this 
case the table for "f" would be empty: (). The compiler will also 
produce a list of such tables for all attributes.

Here there is only one, and the "f" table will have index 0, which is 
what can be used within the byte-code.

The hard part would be in building and maintaining that table. When 
module m is loaded, let's say it defines function "f". Now that can be 
used to create the first entry in the attribute table for "f": ($m, 
$m.f). Here, $m is some internal reference to m, and $m.f is some 
internal reference to m.f().

Now back to resolving m.f(): we know the "m" part is module $m. For "f", 
it looks through its attribute table (remember it's index 0, so instant 
access), and there is only one entry. We're lucky as that entry's owner 
matches the "m." part of this access. So we know it refers to $m.f. No 
lookups by name needed in this case.

However not all random attributes will be neatly defined somewhere as 
functions or classes that will be listed in these little tables. So 
sometimes, an actual lookup will still be needed.

-- 
Bart C



More information about the Python-list mailing list