En Sat, 22 Sep 2007 15:06:38 -0300, George V. Neville-Neil <[EMAIL PROTECTED]> escribi�:
> I have been trying to switch this over to using properties, which seem > at first glance to be cleaner, but which I am having a lot of problems > with. In particular I want to add a property to an object, not a > class. The field list in a class is actually relatively static but I > wind up with ugly code like: > > class ethernet(pcs.Packet): > """Ethernet""" > __layout__ = pcs.Layout() > _map = ethernet_map.map > src = pcs.StringField("src", 48) > dst = pcs.StringField("dst", 48) > type = pcs.Field("type", 16) > > def __init__(self, bytes = None, timestamp = None): > """initialize an ethernet packet""" > > src = pcs.StringField("src", 48) > dst = pcs.StringField("dst", 48) > type = pcs.Field("type", 16) > > pcs.Packet.__init__(self, [dst, src, type], bytes = bytes) > self.description = inspect.getdoc(self) You don't have to repeat the fields: pcs.Packet.__init__(self, [self.dst, self.src, self.type], bytes = bytes) does the same thing. And you can remove self.description=... and use (at the class level): description = __doc__ or: description = property(lambda self: self.__doc__) to automatically enable subclases to share the definition One could say that the field order is important so I'd finally write it as: class ethernet(pcs.Packet): """Ethernet""" __layout__ = pcs.Layout() _map = ethernet_map.map src = pcs.StringField("src", 48) dst = pcs.StringField("dst", 48) type = pcs.Field("type", 16) _fields = [dst, src, type] description = property(lambda self: self.__doc__) def __init__(self, bytes = None, timestamp = None): """initialize an ethernet packet""" pcs.Packet.__init__(self, self._fields, bytes = bytes) > and assigning the properties at class time means that it's hard to > have variations, packets with the same name but with slightly varying > field lists. This is the part I don't understand. Can't you define a new class, in case you want a different field list? Using the above class: class ethernet_modified(ethernet): """Modified ethernet class""" added_field = pcs.StringField("whatever", 16) _fields = [dst, src, type, added_field] And it doesn't even requiere an __init__ method > So, is there a way to assign a property to an object, like this: > > def __init__(.... > self.src = property() > > or something like that? I'd use different classes for different kind of objects. > And, failing that, is there a clean way to modify the class in it's > __init__() method so I don't have to call the Field objects twice, > once for the property effect and once to put into the list in the base > Packet class? I think my example above does what you want. -- Gabriel Genellina -- http://mail.python.org/mailman/listinfo/python-list