2011-10-20 8 views
13

Chciałbym metody w klasie bazowej, aby wywołać inną metodę w tej samej klasie zamiast metody nadpisującej w dziedziczonej klasie. Chciałbym poniższy kod, aby wydrukowaćMetoda dziedziczenia i wywołania metody klasy bazowej python

Klasa B: 6

Klasa A: 9

można to zrobić?


# Base class definition 
class ClassA(object): 
    def __init__(self): 
     print("Initializing A") 

    # hoping that this function is called by this class's printFnX 
    def fnX(self, x): 
     return x**2 

    def printFnX(self, x): 
     print("ClassA:",self.fnX(x)) 

# Inherits from ClassA above 
class ClassB(ClassA): 
    def __init__(self): 
     print("initizlizing B") 

    def fnX(self, x): 
     return 2*x 

    def printFnX(self, x): 
     print("ClassB:", self.fnX(x)) 
     ClassA.printFnX(self,x) 

bx = ClassB() 
bx.printFnX(3) 
+10

Czy zastanawiasz się, która z odpowiedzi została oznaczona jako zaakceptowana? obecny wybór jest naprawdę złym radą dla większości ludzi i większości przypadków użycia. –

Odpowiedz

-3

To samo można osiągnąć, robiąc fnX i printFnX obu metod klas.

class ClassA(object): 

    def __init__(self): 
     print("Initializing A") 

    # hoping that this function is called by this class's printFnX 
    @classmethod 
    def fnX(self, x): 
     return x ** 2 

    @classmethod 
    def printFnX(self, x): 
     print("ClassA:",self.fnX(x)) 

class ClassB(ClassA): 
    def __init__(self): 
     print("initizlizing B") 

    def fnX(self, x): 
     return 2*x 

    def printFnX(self, x): 
     print("ClassB:", self.fnX(x)) 
     ClassA.printFnX(x) 


bx = ClassB()<br> 
bx.printFnX(3) 
+0

To jest lepsze niż inna odpowiedź ... bardziej elegancka. Dzięki. – fodon

+5

To nawet nie działa. Spróbuj uzyskać dostęp do zmiennej instancji takiej jak '' self.y'' z wnętrza fnX. W metodzie class zmienna * self * nie zawiera już instancji; zamiast tego staje się klasą instancji wywołującego, więc całkowicie straciłeś dostęp do zmiennych instancji. Ten "wzór" to katastrofa i coś, czego nie powinno się używać w kodzie, na którym ci zależy. –

+0

Zgadzam się, odpowiedział właśnie na jego oryginalne pytanie, to jest z wszystkimi wadami, które właśnie opisałeś. Nie ma tutaj żadnego wzorca per se. –

49

Gratulacje, odkrył motywującą przypadek użycia dla Pythona nazwy dwukrotnie podkreślenia maglowania :-)

Dla szczegółów i wypracowaną przykład patrz: http://docs.python.org/tutorial/classes.html#private-variables i na http://docs.python.org/reference/expressions.html#atom-identifiers.

Oto jak go używać na swojej przykład:

# Base class definition 
class ClassA(object): 
    def __init__(self): 
     print("Initializing A") 

    # hoping that this function is called by this class's printFnX 
    def fnX(self, x): 
     return x**2 
    __fnX = fnX 

    def printFnX(self, x): 
     print("ClassA:",self.__fnX(x)) 

# Inherits from ClassA above 
class ClassB(ClassA): 
    def __init__(self): 
     print("initizlizing B") 

    def fnX(self, x): 
     return 2*x 

    def printFnX(self, x): 
     print("ClassB:", self.fnX(x)) 
     ClassA.printFnX(self,x) 

bx = ClassB() 
bx.printFnX(3) 

Sprawa zastosowanie opisano jako sposób realizacji Open-Closed Principle w „The Art of instacji” znaleziono w http://www.youtube.com/watch?v=yrboy25WKGo&noredirect=1.

+1

Bardzo wnikliwe. Teraz wiem, jakie podwójne nazywanie metod jest użyteczne! –

+0

Co może nie być oczywiste, że metody w klasie bazowej muszą być publiczne lub musisz użyć w pełni zmanipulowanej nazwy. Python nie ma kwalifikatora "chronionego" lub "znajomego", więc gdy refaktoryzacja po prostu przesuwając 'def __doSomething (self): 'z super klasy do klasy bazowej, nie będzie dostępna dla super klasy. Będziesz musiał albo upublicznić 'def doSomething (self): 'albo użyć sfałszowanej nazwy. –

Powiązane problemy