W Pythonie 2.5 poniższy kod wywołuje TypeError
:
>>> class X:
def a(self):
print "a"
>>> class Y(X):
def a(self):
super(Y,self).a()
print "b"
>>> c = Y()
>>> c.a()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 3, in a
TypeError: super() argument 1 must be type, not classobj
Gdybym wymienić class X
z class X(object)
, to będzie działać. Jakie jest tego wytłumaczenie?
Odpowiedzi:
Powodem jest to, że
super()
działa tylko na klasach w nowym stylu , co w serii 2.x oznacza rozszerzenie zobject
:źródło
Ponadto nie używaj super (), chyba że musisz. Nie jest to „właściwa rzecz” ogólnego przeznaczenia w przypadku klas w nowym stylu, co można by podejrzewać.
Są chwile, kiedy spodziewasz się wielokrotnego dziedziczenia i możesz tego chcieć, ale dopóki nie poznasz włochatych szczegółów MRO, najlepiej zostaw to w spokoju i trzymaj się:
źródło
__init__
), aby przekazywać argumenty w czysty i rozsądny sposób, w przeciwnym razie otrzymasz TypeErrors lub gorsze problemy z debugowaniem, gdy ktoś spróbuje pomnożyć-dziedziczenie przy użyciu Twojej klasy. O ile naprawdę nie zaprojektowałeś obsługi MI w ten sposób (co jest dość trudne), prawdopodobnie lepiej jest uniknąć sugestiisuper
, że metoda jest bezpieczna dla MI.W przypadku, gdy żadna z powyższych odpowiedzi nie wskazywała tego wyraźnie. Twoja klasa nadrzędna musi dziedziczyć po „obiekcie”, co zasadniczo zmieniłoby ją w nową klasę stylu.
źródło
Wypróbowałem różne metody Xa (); jednak wydają się one wymagać wystąpienia X w celu wykonania (), więc zrobiłem X (). a (self), co wydaje się bardziej kompletne niż poprzednie odpowiedzi, przynajmniej w przypadku aplikacji, które napotkałem. Wydaje się, że nie jest to dobry sposób na rozwiązanie problemu, ponieważ występuje niepotrzebna budowa i zniszczenie, ale działa dobrze.
Moją aplikacją był moduł cmd.Cmd w Pythonie, który z jakiegoś powodu najwyraźniej nie jest obiektem NewStyle.
Ostateczny wynik:
źródło