Stephen Hansen said:


    But http://docs.python.org/tutorial/classes.html says, in Section
    9.3 "A First Look at Classes":

    When a class definition is entered, a new namespace is created,
    and used as the local scope — thus, all assignments to local variables
    go into this new namespace. In particular, function definitions bind
    the name of the new function here.

[snip]

    (BTW, Diez, your toy example is another demonstration that there
    *is* a class-scope-lookup: the "def" statement binds the name
    "fact" in the class scope, and the assignment statement looks up
    the name "fact" in that scope.)


This sounds like a fundamental confusion -- a namespace is not equivalent to a scope, really, I think.

My apologies if I was being too loose with the terms "namespace" and "scope". I was trying to use Diez's terminology (e.g. "class-scope-lookup"). But I think you agree with me in *almost* everything you say below.


The def statement creates a function object, and assigns it to the given name, in its /local scope/ which is the class's namespace -- but that is not a new scope. Its just, during class creation, the local scope.

When you enter a class definition, a new namespace is created, and that is used as the local scope during the class's definition. Under "class Foo", the local scope is this class's namespace-- and the global scope is the module's namespace. Any lookup operation checks first in the local scope, then in the global scope... When the "def fact(...)" is executed (note that class bodies are executed on load, function bodies aren't), a new namespace is created as well-- the function's namespace-- and its used as the local scope. During execution of the code, it looks up in the local scope first-- and then it looks up in the global scope if it doesn't find anything. There /is/ no class-lookup-scope... but there IS a class namespace.

There's just those two scopes: but the namespace bound to those scopes changes as you enter different parts of the code. For a long time that's all there was, just the local and global scope: to access any other namespace required you to explicitly address it. The class namespace remains accessible only via explicit addressing, but PEP 227 in Python 2.1/2.2 introduced static nested scopes. But that applies only to enclosing functions: embedding one function into another.

You can only call recursive functions if the function is able to refer to itself according to the same lookup rules: is the function's name in the local scope? No it's not... is it in the global scope? No? Then it can't call itself recursively... well, unless its a method, and it addresses itself specifically-- with "self.".

All of the above is consistent with my previous post.


The OP's probably is that during the execution of the class body, the class doesn't exist... so the 'def fact' -can't- use Classname.fact to address itself explicitly, and within fact the locals don't contain a reference to the function itself, and its globals don't either. You just can't do that.

Here's where we disagree, and I'm sticking to my guns. The fact that the class definition has not been completely processed is irrelevant. The OP's problem was attempting to implement a recursive function. A non-recursive implementation of fact() works fine:

class ThisWorks(object):
   def fact(n):
       answer = 1
       i = 1
       while i <= n:
           answer *= i
           i += 1
       return answer

   clsvar = fact(4)

print ThisWorks.clsvar  # output: 24


The right way, IMHO, is to move 'fact' up and out of the class ...

We're back to agreement on this point!

-John

--
http://mail.python.org/mailman/listinfo/python-list

Reply via email to