どのメソッドも を呼び出す必要がない場合、これは Python の多重継承で行うことができますsuper()
。
class Dog(object):
name = "Spot"
class Cat(object):
name = "Whiskers"
class SpeakingAnimalMixin(object):
def speak(self):
print "My name is", self.name, "and I can speak!"
class SpeakingDog(SpeakingAnimalMixin, Dog):
pass
class SpeakingCat(SpeakingAnimalMixin, Cat):
pass
SpeakingDog().speak()
私の名前はスポットです。話すことができます。
メソッドから呼び出す必要がある場合はsuper()
、クラスを動的に作成する必要があります。これは問題なく機能しますが、生成されたクラスの名前はあまり役に立たず、IDE やその他の静的分析ツールはあまり役に立たない可能性があります。
関数を使用してクラスを作成し、スーパークラスを引数として渡すことができます。
def make_speaking_animal_class(SpeechlessAnimal):
class SpeakingAnimal(SpeechlessAnimal):
def get_name(self):
return "Speaking " + super(SpeakingAnimal, self).get_name()
def speak(self):
print "My name is", self.get_name()
return SpeakingAnimal
class Dog(object):
def get_name(self):
return "Spot"
class Cat(object):
def get_name(self):
return "Whiskers"
SpeakingDog = make_speaking_animal_class(Dog)
SpeakingCat = make_speaking_animal_class(Cat)
SpeakingCat().speak()
私の名前は話すひげです
ただし、前述のように、クラスの__name__
属性は期待どおりではない場合があります。
print SpeakingDog
print SpeakingDog()
<class '__main__.SpeakingAnimal'>
<__main__.SpeakingAnimal object at 0x1004a3b50>
__name__
これは、一意の属性を自分で割り当てることで修正できます。
SpeakingDog.__name__ = 'SpeakingDog'
print SpeakingDog
<class '__main__.SpeakingDog'>
(回答でこれを提案したAndrew Jaffeの功績ですが、彼はそれを削除しました。)
クラスを動的に作成する別の方法がありますが、必要でない限り使用しないことをお勧めします。それはさらに明確ではありません。このtype
関数には、オブジェクトのクラスを決定するという主な用途とは別に、2 つ目の用途があります。新しいクラスを動的に作成するために使用できます。
このように使用すると、type
関数は次の 3 つのパラメーターを受け取ります。
name
、__name__
新しいクラスが持つことになります。
bases
、新しいクラスが継承する基本クラスのタプル。
dict
、新しいクラスが持つメソッドと属性を含む辞書。
次のように使用できます。
def make_speaking_animal_class(SpeechlessAnimal, name):
def get_name(self):
return "Speaking " + super(SpeakingAnimal, self).get_name()
def speak(self):
print "My name is", self.get_name()
bases = (SpeechlessAnimal,)
# We need to define SpeakingAnimal in a variable so that get_name can refer
# to it for the super() call, otherwise we could just return it directly.
SpeakingAnimal = type(name, bases, {
'get_name': get_name,
'speak': speak
})
return SpeakingAnimal
class Dog(object):
def get_name(self):
return "Spot"
class Cat(object):
def get_name(self):
return "Whiskers"
SpeakingDog = make_speaking_animal_class(Dog, 'SpeakingDog')
SpeakingCat = make_speaking_animal_class(Cat, 'SpeakingCat')
SpeakingDog().speak()
SpeakingCat().speak()
僕の名前はスピーキングスポット
僕の名前はスピーキングウィスカーズ