howto prevent class variable assignment

U

Uwe Mayer

Hi,

when an instance variable of a class is not found, python tries to fall back
to the class variable.
I want to use that feature to provide default settings for a class which can
be overwritten by assignments to variables with the same name.

This quickly becomes difficult to handle when you get confused wether your
assignment was made to a class variable or an instance variable. I
therefore want to prevent write access to class variables. How do I do
that?

Here some example code:
.... cInt = 5
.... cList = [1,2,3]
.... def __init__(self):
.... self.cInt = 6
....
5
a.cList[2] = 5 #<-- prevent this
a.cList
[1, 2, 5]

I tried to overwrite __setattr__(self, name, value) method, but this is only
called if I call it on an instance, i.e.

but not when I call it on the class:


Can anyone give me some pointers or suggentions how to handle this?

Thanks
Uwe
 
G

Gerrit Holl

Uwe said:
when an instance variable of a class is not found, python tries to fall back
to the class variable.
I want to use that feature to provide default settings for a class which can
be overwritten by assignments to variables with the same name.

This quickly becomes difficult to handle when you get confused wether your
assignment was made to a class variable or an instance variable. I
therefore want to prevent write access to class variables. How do I do
that?

I think you can do that with a Metaclass.
See http://www.python.org/2.2.2/descrintro.html#metaclasses

Gerrit.
 
P

Peter Otten

Uwe said:
when an instance variable of a class is not found, python tries to fall
back to the class variable.
I want to use that feature to provide default settings for a class which
can be overwritten by assignments to variables with the same name.

This quickly becomes difficult to handle when you get confused wether your
assignment was made to a class variable or an instance variable. I
therefore want to prevent write access to class variables. How do I do

The sane way would be to copy mutable defaults in __init__().
that?

Here some example code:
... cInt = 5
... cList = [1,2,3]
... def __init__(self):
... self.cInt = 6
...
a = A()
a.cInt 6
a.__class__.cInt
5
a.cList[2] = 5 #<-- prevent this

I fear this is *hard* as you are just changing an instance of a mutable
class. Maybe you could write a general readonly wrapper?
[1, 2, 5]

I tried to overwrite __setattr__(self, name, value) method, but this is
only called if I call it on an instance, i.e.

but not when I call it on the class:


Can anyone give me some pointers or suggentions how to handle this?

A is an instance of its metaclass, so you have to devise a way to prevent
write access for metaclass instances.

Below is an example that uses the "sealed" attribute to prevent further
write access when you are done defining the class:
.... def __setattr__(self, name, value):
.... if hasattr(self, "sealed"):
.... raise Exception("Attempt to set class att
ribute")
.... type.__setattr__(self, name, value)
........ __metaclass__ = Type
.... x = 123
.... y = 456
....Traceback (most recent call last):
File "<stdin>", line 1, in ?

Again, this will not prevent changing a mutable instance, e. g. setting a
list item. Your time is probably better spend on writing a good test suite
for your app.

Peter
 

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,770
Messages
2,569,583
Members
45,074
Latest member
StanleyFra

Latest Threads

Top