Classes with initialization

  • Thread starter mariano.suarezalvarez
  • Start date
M

mariano.suarezalvarez

Hi all,

I'm currently using code similar to this:

class ClassWithInitialization(type):
def __init__(cls, name, bases, dict):
type.__init__(name, bases, dict)
dict['__class_init__'](cls)

class A:
__metaclass__ = ClassWithInitialization

def __class_init__(cls):
cls.some_attribute = ...
...

in order to get class attributes initialized (since the values of
these attributes
need non trivial work to be computed, putting the code that does that
computation in the class scope ends up with the class having extra
attributes---the `local' variables used in the computation of the
values of class attribute; so I'm using __class_init__'s scope to
contain those variables)

I was wondering: is there a simpler approach to this?

Also: can someone enlighten me as to when code in class scope is run,
exactly?
if a class A has a metaclass M, then M.__init__ does not seem to get
the code in A's class scope in its arguments AFAICS, so I guess that
code is run before the class is created?

Cheers,

-- m
 
K

kyosohma

Hi all,

I'm currently using code similar to this:

class ClassWithInitialization(type):
def __init__(cls, name, bases, dict):
type.__init__(name, bases, dict)
dict['__class_init__'](cls)

class A:
__metaclass__ = ClassWithInitialization

def __class_init__(cls):
cls.some_attribute = ...
...

in order to get class attributes initialized (since the values of
these attributes
need non trivial work to be computed, putting the code that does that
computation in the class scope ends up with the class having extra
attributes---the `local' variables used in the computation of the
values of class attribute; so I'm using __class_init__'s scope to
contain those variables)

I was wondering: is there a simpler approach to this?

Also: can someone enlighten me as to when code in class scope is run,
exactly?
if a class A has a metaclass M, then M.__init__ does not seem to get
the code in A's class scope in its arguments AFAICS, so I guess that
code is run before the class is created?

Cheers,

-- m

As I understand it, class code doesn't get run until you create an
instance of the class and call a method with that instance. I don't
know how to answer your other question though.

Mike
 
M

Michele Simionato

Hi all,

I'm currently using code similar to this:

class ClassWithInitialization(type):
def __init__(cls, name, bases, dict):
type.__init__(name, bases, dict)
dict['__class_init__'](cls)

class A:
__metaclass__ = ClassWithInitialization

def __class_init__(cls):
cls.some_attribute = ...
...

in order to get class attributes initialized (since the values of
these attributes
need non trivial work to be computed, putting the code that does that
computation in the class scope ends up with the class having extra
attributes---the `local' variables used in the computation of the
values of class attribute; so I'm using __class_init__'s scope to
contain those variables)

I was wondering: is there a simpler approach to this?

Yes, see http://www.phyast.pitt.edu/~micheles/python/classinitializer.html
Also: can someone enlighten me as to when code in class scope is run,
exactly?
if a class A has a metaclass M, then M.__init__ does not seem to get
the code in A's class scope in its arguments AFAICS, so I guess that
code is run before the class is created?

Cheers,

__init__ is run after class creation. What does not work exactly?

Michele Simionato
 
A

Alex Martelli

It's run as a part of the execution of the class statement.

Right. Nutshell 2nd ed, p 83 under "The class statement":

"""
The nonempty sequence of statements that follows the class statement is
known as the class body. A class body executes immediately as part of
the class statement's execution. Until the body finishes executing, the
new class object does not yet exist and the classname identifier is not
yet bound (or rebound). "How a Metaclass Creates a Class" on p. 118
provides more details about what happens when a class statement
executes.
"""

The key to the latter part of the explanation (which actually starts on
p. 117:) is that the class body executes in a temporary dictionary, say
d; that d is then used to help determine the meclass M (it may direct it
by having a key '__metaclass__'); then, d is passed as one of the three
arguments to the call to M (preceded by the classname string and the
tuple of the class's bases) -- lastly, the classname is bound or rebound
to the result of that call.
As I understand it, class code doesn't get run until you create an
instance of the class and call a method with that instance. I don't

No, this delay applies to code that's part of methods defined in the
class, but not to code that appears directly in classbody. Easy to
check:
.... print 'hello world'
....
hello world
As you see, although no instance of the class has yet been created, the
print statement that's directly in classbody has already run. If you
want to check that it runs _before_ the metaclass gets called, set a
custom metaclass that also does a print in its __init__, and see in what
order the print statements execute...


Alex
 
C

Carl Banks

Hi all,

I'm currently using code similar to this:

class ClassWithInitialization(type):
def __init__(cls, name, bases, dict):
type.__init__(name, bases, dict)
dict['__class_init__'](cls)

class A:
__metaclass__ = ClassWithInitialization

def __class_init__(cls):
cls.some_attribute = ...
...

in order to get class attributes initialized (since the values of
these attributes
need non trivial work to be computed, putting the code that does that
computation in the class scope ends up with the class having extra
attributes---the `local' variables used in the computation of the
values of class attribute; so I'm using __class_init__'s scope to
contain those variables)

I was wondering: is there a simpler approach to this?

You could put the computations right in the class, and del the extra
variables when done.


Carl Banks
 

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

Forum statistics

Threads
473,770
Messages
2,569,583
Members
45,072
Latest member
trafficcone

Latest Threads

Top