Python中的多态性

时间:2020-01-09 10:44:19  来源:igfitidea点击:

在这篇文章中,我们将看到OOPS概念多态在Python中的用法。

什么是多态

多态性是希腊语单词,其中poly表示"许多",而morph表示"从一种形式变为另一种形式"。用面向对象的术语,它涉及采用多种形式(分配给不同类型)的同一对象引用,一种具有相同名称的方法具有多个实现,运算符对不同操作数的行为也不相同。

Python中的多态性

在面向对象的语言中,我们可能会看到以下列方式之一使用多态性

  • 方法重载,也称为编译时多态

  • 方法覆盖,也称为运行时多态

  • 运算符重载

在Python中,我们可以通过方法重写和运算符重载找到对多态的支持。 Python不支持传统意义上的方法重载。同样,在讨论Python中的多态性时,我们还应该了解Python中的鸭子类型。因此,让我们来看一些示例。

编译时多态(方法重载)

方法重载意味着在一个类中有多个具有相同名称的方法。这些重载方法的类型或者传递的参数数量不同。
Python不支持编译时多态或者方法重载。如果一个类中有多个具有相同名称的方法,则只能识别最后定义的方法。调用任何其他重载方法都将导致错误。

在这篇文章中阅读有关Python中方法重载的更多信息

运行时多态(方法覆盖)

在继承的情况下,子类继承父类的所有属性和方法。如果子类中有一个方法具有与父类相同的名称和参数数量,则此过程称为"方法重写",其中子类方法被称为覆盖了父类方法。

在这篇文章中阅读有关Python中方法重写的更多信息

当我们使用父类对象调用重写的方法时,将执行父类的方法。用子类对象调用相同的方法时,子类的方法被执行。因此,根据对象类型调用适当的重写方法,这是运行时多态性的一个示例。

考虑以下类层次结构,其中超类Animal具有两个方法info()和make_sound()。有两种覆盖这两种方法的子类:Duck和Dog。

class Animal:
    def info(self):
        print('I am an animal')

    def make_sound(self):
        pass

class Duck(Animal):
    def info(self):
        print('I am a Duck')

    def make_sound(self):
        print('Quack Quack')

class Dog(Animal):
    def info(self):
        print('I am a Dog')

    def make_sound(self):
        print('Bow Wow')

d = Duck()
d.info()
d.make_sound()
d = Dog()
d.info()
d.make_sound()

输出:

I am a Duck
Quack Quack
I am a Dog
Bow Wow

当d引用Duck的一个对象时,它调用Duck类的方法,当d引用Dog的一个对象时,它调用该类的方法。

通过运算符重载实现Python中的多态

运算符重载也是多态的一个示例,其中同一运算符根据操作数的类型执行不同的运算。 Python支持运算符重载。

例如," +"运算符

  • 与数字一起使用时,它将执行加法运算。

  • 与两个字符串一起使用时,将这些字符串连接起来

  • 与列表一起使用时,合并这些列表

# + operator with integers- Addition
print(3 + 4)
# + operator with Strings- Concatenation
print("Operator " + "Overloading")
a = [10, 11, 12]
b = [100, 200, 300]
# + operator with Lists- Merging
print(a + b)

输出:

7
Operator Overloading
[10, 11, 12, 100, 200, 300]

Duck typing和多态性

Python遵循鸭子的输入哲学,该哲学指出"如果它走路像鸭子,而像鸭子一样嘎嘎叫,那么它一定是鸭子"。

在像Python这样的动态语言中,这意味着我们不必担心对象的类型或者类。是否可以对对象执行必需的操作更为重要。

由于Python遵循了这种鸭子输入原则,因此可以创建一个可以接受任何对象的函数,从而实现多态。只要传递的对象具有被调用的方法,就可以对其进行调用。让我们用一个示例来清除它,其中有两个类带有make_sound()方法。有一个函数调用,它将任何对象作为参数并对该对象调用make_sound()方法。当使用Duck类的对象的对象调用invoke函数时,将调用Duck类的make_sound()方法,而当使用Dog类的对象的Dog对象的调用make_sound()方法时,则调用Dog类的make_sound()方法。

class Duck:
    def make_sound(self):
        print("Quack Quack")

class Dog:
    def make_sound(self):
        print('Bow Wow')

def invoke(obj):
    obj.make_sound()

d = Duck()
invoke(d)
d = Dog()
invoke(d)

输出:

Quack Quack
Bow Wow