[Python-3000] Fixing super anyone? (reflux) (original) (raw)
Guido van Rossum guido at python.org
Thu Apr 26 21:06:45 CEST 2007
- Previous message: [Python-3000] Fixing super anyone? (reflux)
- Next message: [Python-3000] Fixing super anyone?
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]
Writing B.super.f(self) instead of super(B, self).f() is not an improvement.
On 4/26/07, Joel Bender <jjb5 at cornell.edu> wrote:
I've come late to this thread, and misunderstood what was wrong with super(), so a thousand pardons please. But since that's never stopped me before...
Guido van Rossum wrote: > But: > > class E(D): pass > > print E().f() > > This prints DDBCA which surely isn't right. > > Sounds like the classic bug in such attempts. About about this? class super(property): def init(self): property.init(self, self.getsuper, None, None) def getsuper(self, klass): class wrapper: def getattr(self, fn): self.fn = fn return self def call(self, obj, *args, **kwargs): mro = iter(obj.class.mro) for cls in mro: if cls is klass: break for cls in mro: f = getattr(cls, self.fn) if f: return f(obj, *args, **kwargs) raise AttributeError, self.fn return wrapper() class superable(type): super = super() class A(object): metaclass = superable def f(self): return "A" class B(A): def f(self): return "B" + B.super.f(self) class C(A): def f(self): return "C" + C.super.f(self) class D(B, C): def f(self): return "D" + D.super.f(self) class E(D): pass assert E().f() == "DBCA"
Tim Delaney wrote: > What I haven't worked out yet is if you should be able to do > the following: > > class A(autosuper): > def f(self): > print 'A:', super > > class B(A): > def f(self): > def inner(): > print 'B:', super > super.f() > inner() And here's my version: class A(object): metaclass = superable def f(self): return "A" class B(A): def f(self): def inner(): return "B" + B.super.f(self) inner() assert B().f() == "BA" Now, back to the original request, I came up with this: def super(klass, obj=None): class wrapper: def init(self): self.klass = klass self.obj = obj def getattr(self, fn): self.fn = fn return self def call(self, *args, **kwargs): if not self.obj: self.obj = args[0] args = args[1:] mro = iter(self.obj.class.mro) for cls in mro: if cls is self.klass: break for cls in mro: f = getattr(cls, self.fn) if f: return f(self.obj, *args, **kwargs) raise AttributeError, self.fn return wrapper() class A(object): def f(self): return "A" class B(A): def f(self): return "B" + super(B).f(self) class C(A): def f(self): return "C" + super(C, self).f() class D(B, C): def f(self): return "D" + super(D, self).f() class E(D): pass assert E().f() == "DBCA" I prefer the version in C, but B works as well. Comments? Is this ground that has already been covered? Joel
Python-3000 mailing list Python-3000 at python.org http://mail.python.org/mailman/listinfo/python-3000 Unsubscribe: http://mail.python.org/mailman/options/python-3000/guido%40python.org
-- --Guido van Rossum (home page: http://www.python.org/~guido/)
- Previous message: [Python-3000] Fixing super anyone? (reflux)
- Next message: [Python-3000] Fixing super anyone?
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]