On Wednesday 14 January 2009 11:45:46 am Paul Rubin wrote: > Luis Zarrabeitia <ky...@uh.cu> writes: > > Why don't you do it backwards? > > You *can* implement a metaclass that will remove the dynasmism from its > > instances. Do it - I can give you a starting point if you wish. > > That's kind of interesting, how does it work?
Proof of concept, that breaks on inheritance (can't call 'super'), but it took me just a few minutes to cook. If you aren't that paranoid, you could get rid of the 'currentframe' and 'code' hacks. This creates a class "MyClass" which instances cannot be modified. I once gave my students the homework of creating a metaclass that would type-check all the assignments to its members - so that the types wouldn't change. ======== import inspect class ImmutableType(type): def __init__(self, *args, **kwds): super(ImmutableType, self).__init__(*args, **kwds) initmethod = self.__init__.im_func def setattr(instance, attr, value): callee = inspect.currentframe(1) #letting the initializer if callee.f_code is initmethod.func_code: #initialize the object super(self, instance).__setattr__(attr, value) else: raise Exception("Object is immutable") self.__setattr__ = setattr # Heh, I'm adding a dynamic attribute :D class MyClass(object): __metaclass__ = ImmutableType a = 5 def __init__(self, value): print "assigning b" self.b = value print self.b m = MyClass("can't change") print m.a, m.b # these work m.b = 6 # and these dont. m.c = 8 ========== > > But most of us are very happy with the dynamic nature of python... I > > chose python _because_ of it. > > I like it too, since it is indispensable in some situations. But, > those situations are uncommon enough that I don't mind typing a few > extra keystrokes to turn the dynamism on. I find the opposite to be true. I _usually_ want the dynamism. Even if I'm not using it - I rely on the dynamism to be there for when I need it. > > Btw, for performance, there is __slots__, > > That is a good point, we somehow lost sight of that in this thread. > > > with the side-effect that it forbids attribute creation 'on the > > fly'. > > I have had the impression that this is a somewhat accidental side > effect and shouldn't be relied on. Yes, accidental side effect. But I see no _necessary_ harm on tacking extra attributes to an existing object - specially if you are going to use them pretty close to the creation. I use them, a lot, specially when writing decorators... Many times I just want to 'mark' the decorated functions so I can inspect those marks later. I'd rather have a semi-private namespace for each pair ([group of]calling function[s], object), but it is way easier (and so far, maintanable) to just add an appropriately named dynamic attribute to the object. Of course there can be harm - but the fault lies on the user and not the tool. I specially dislike that I can't add dynamic attributes to an object(). -- Luis Zarrabeitia (aka Kyrie) Fac. de Matemática y Computación, UH. http://profesores.matcom.uh.cu/~kyrie -- http://mail.python.org/mailman/listinfo/python-list