Steven D'Aprano a écrit : > On Sun, 24 Jul 2005 12:07:02 +0300, Thanos Tsouanas wrote: >> >>>Thanos Tsouanas wrote: >>> (snip) >>I didn't know about it, but I knew about object.__dict__ which is, as I >>see equivalent with vars(object). But it doesn't do the job for me, >>since it fails to grab all obj.foo's, some of them being properties, >>etc. > (snip) > I don't think you are correct. As far as I can see, properties do have > an entry in obj.__dict__ the same as other attributes, although there is > certainly some strangeness going on with properties. > > Using the sample code from here: > http://www.python.org/2.2.3/descrintro.html#property > > class C(object): > def __init__(self): > self.__x = 0 > def getx(self): > return self.__x > def setx(self, x): > if x < 0: x = 0 > self.__x = x > x = property(getx, setx) > > I see _C__x in C().__dict__, exactly as expected. (snip)
Yes, but you don't see 'x'. Poking into the object's __dict__ would defeat the whole point of computed attributes - which by the way need not directly map to a protected or private variable, nor even be properties (think: descriptors). > I can't see any way to inspect a Python object and get a list of > properties, I do : def list_properties(obj): proptype = type(property()) # not defined in types klass = obj.__class__ names = dir(klass) # so we get inherited attribs as well d = dict([(name, getattr(klass, name)) for name in names]) return [name for name, attrib in d.items() \ if type(attrib) is proptype] Note that this won't find all descriptors (I've tried and it really harder... there are a lot of things in a class.__dict__ that have a __get__() method, most of'em not defined in the types module). Anyway, you won't need it... (I mean, the OP don't need it to solve it's problem) > so you might have to keep your own list: add a class-attribute > of your object which keeps a list of all the properties: > > class Obj: > # various methods, attributes and properties > ... > # keep a list of special properties that don't show > # up correctly in __dict__ > special = ['foo', 'bar'] > > # now define a special method that makes a copy of > # __dict__ and adds special properties to it > > def objdict(self): > D = self.__dict__.copy() > # assume shallow copy is enough > for property_name in self.special: > D[property_name] = self.__getattribute__(property_name) > return D > > then call it when you need it: > > print "My object has fields %(foo)s and %(bar)s." % obj.objdict() This means adding responsabilities to the class when the need is obviously orthogonal to the class's responsabilities. Implementing a generic decorator pattern in Python does'nt require more code, doesn't requires the class nor the object to be modified at all, is probably more robust, and is, well... more generic !-) (should I say 'more pythonic' ?) > It would be nice to see an easier way to introspect objects and get > a list of properties. You're dream is now reality. Now ain't *that* nice ?-) Bruno -- http://mail.python.org/mailman/listinfo/python-list