2009-07-23 3 views
26

Disons que j'ai les classes suivantes mis en place:Quel est un exemple de base de l'héritage unique en utilisant le mot-clé super() dans Python?

class Foo: 
    def __init__(self, frob, frotz): 
      self.frobnicate = frob 
      self.frotz = frotz 
class Bar: 
    def __init__(self, frob, frizzle): 
      self.frobnicate = frob 
      self.frotz = 34 
      self.frazzle = frizzle 

Comment puis-je (si je peux tout) utiliser super() dans ce contexte pour éliminer le code en double?

+0

[http://stackoverflow.com/questions/904036/chain-calling-parent-constructors-in-python](http://stackoverflow.com/questions/904036/chain-calling-parent-constructors-in-python) –

Répondre

25

En Python> = 3.0, comme ceci:

class Foo(): 
    def __init__(self, frob, frotz) 
     self.frobnicate = frob 
     self.frotz = frotz 

class Bar(Foo): 
    def __init__(self, frob, frizzle) 
     super().__init__(frob, 34) 
     self.frazzle = frizzle 

En savoir plus ici: http://docs.python.org/3.1/library/functions.html#super

EDIT: Comme l'a dit dans une autre réponse, parfois simplement en utilisant Foo.__init__(self, frob, 34) peut être la meilleure solution. (Par exemple, lorsque vous travaillez avec certaines formes d'héritage multiple.)

+9

Juste pour être clair, ce n'est que python> = 3.0. Pour les pythons plus anciens (mais seulement ceux avec des "classes de style nouveau"), la réponse @ire_and_curses décrit ce qui doit être fait. –

29

En supposant que vous voulez Bar de classe pour définir la valeur 34 dans son constructeur, cela fonctionnerait:

class Foo(object): 
    def __init__(self, frob, frotz): 
      self.frobnicate = frob 
      self.frotz = frotz 

class Bar(Foo): 
    def __init__(self, frob, frizzle): 
      super(Bar, self).__init__(frob, frizzle) 
      self.frotz = 34 
      self.frazzle = frizzle 


bar = Bar(1,2) 
print "frobnicate:", bar.frobnicate 
print "frotz:", bar.frotz 
print "frazzle:", bar.frazzle 

Cependant, super introduit son propre complications. Voir par exemple super considered harmful. Pour être complet, voici la version équivalente sans super.

class Foo(object): 
    def __init__(self, frob, frotz): 
      self.frobnicate = frob 
      self.frotz = frotz 

class Bar(Foo): 
    def __init__(self, frob, frizzle): 
      Foo.__init__(self, frob, frizzle) 
      self.frotz = 34 
      self.frazzle = frizzle 


bar = Bar(1,2) 
print "frobnicate:", bar.frobnicate 
print "frotz:", bar.frotz 
print "frazzle:", bar.frazzle 
+1

Pourquoi définissez-vous Bar.frotz = frizzle à travers le constructeur de super classe puis en le mettant à 34 séparément? ne devriez-vous pas avoir __init __ (frob, 34)? – Victor

+2

Oui, cela fonctionnerait aussi, et serait plus propre. L'exemple est plutôt artificiel (définissant une constante dans un constructeur), mais j'essayais de rester aussi proche de l'original que possible. –

+0

Je ne sais pas si c'est un bon moyen de le faire ... considérez le cas où le super constructeur exécute une opération sur frotz et que frizzle est une classe, votre code ne fonctionnera pas ou bien pire pourrait arriver. – Victor

Questions connexes