Newbie again: computing attributes on the fly

Gordon McMillan gmcm at hypernet.com
Wed Jun 16 15:58:44 EDT 1999


[Olaf on my very simple getattr hack]:

> Yes, I definitely want to generalize that. The problem is that that
> method may be defined in a superclass, so "self.__dict__" won't find
> it. AFAIK (which may be not be very far), I have to use "hasattr"
> and/or "getattr", which in turn will call "__getattr__".

Oh, getattr isn't bad. Wait 'till you try setattr! Anyway, this 
should demonstrate how to control the recursion:

class X:
  def __getattr__(self, nm):
    print "Looking for", nm
    mthdnm = "calc_%s" %nm
    print "Looking in instance..."
    mthd = self.__dict__.get(mthdnm, None)
    if mthd is None:
      print "Looking in class hierarchy..."
      try:
        mthd = getattr(self.__class__, mthdnm)
      except AttributeError:
        pass
    if mthd:
      val = mthd(self)
      self.__dict__[nm] = val
      return val
    raise AttributeError("no attribute %s" % nm)

x = X()
try:
  print x.foo
except AttributeError:
  print "foo not found in x"

class Y(X):
  def calc_foo(self):
    return 33.0 * 17

y = Y()
print y.foo
print "second time..."
print y.foo

Which should yield:

Looking for foo
Looking in instance...
Looking in class hierarchy...
foo not found in x
Looking for foo
Looking in instance...
Looking in class hierarchy...
561.0
second time...
561.0

- Gordon




More information about the Python-list mailing list