4.2 类的继承
在编程中,类的好处我们知道了,通过类我们可以源源不断的实例化出对象,这些对象用有相同的属性和方法,大大提高了程序代码的复用性。
在某些情况下,如果想要创建一个新的类,这个类除了要有旧类的所有属性和方法,还有一些其他的属性和方法,那么重新再去定义它显示是不明智的,这个时候可以通过继承来实现。
继承是指一种代码组织方式,它允许同一个类中的成员共享它们的方法和数据结构。在编程中,继承通常是指使用同一个类的成员来创建新的类,而不是创建一个新的类。这是因为继承可以使代码更易于编写和维护,并且可以简化代码组织方式。继承的优点:
- 增强代码的可扩展性:通过使用继承,可以创建多种不同类型的类,这些类可以被扩展到不同的应用场景。
- 提高代码的可维护性:通过使用继承,可以将相同类型的对象划分为多个小类,从而提高代码的可维护性。
举个例子:现在创建了一个动物类:Animal,这个动物类具有两个方法,分别是吃
喝睡
,那么在程序中可以如此定义:
class Animal:
def eat(self):
print('我饿了')
def sleep(self):
print('我困了')
animal = Animal()
animal.eat()
animal.sleep()
我饿了
我困了
一般动物都具有这2个方法,这个Animal
作为动物类的模板,具有动物最基本的方法。这个时候如果还要创建新的类,比如哺乳动物类、鸟类,那么就可以通过继承动物类来创建:
class Mammal(Animal):
def walk(self):
print('我会走')
class Bird(Animal):
def fly(self):
print('我会飞')
mammal = Mammal()
bird = Bird()
mammal.walk()
mammal.sleep()
bird.fly()
bird.eat()
我会走
我困了
我会飞
我饿了
我们看到,哺乳动物类和鸟类都继承了动物类的eat
和sleep
方法,而他们各自又新建了新方法,分别是walk
和fly
。
在上面的例子中,Animal类
被Mammal类
和Bird类
继承,则称Animal类
是Mammal类
和Bird类
的父类
、基类
或超类
。而Mammal类
和Bird类
是Animal类
的子类
。
注意,子类是无法继承父类的私有属性和私有方法的:
from icecream import ic
class Animal:
def __init__(self):
self.a = 'A'
self.__b = 'B'
def __eat(self):
ic('我饿了')
def sleep(self):
ic('我困了')
class Mammal(Animal):
...
mammal = Mammal()
ic(mammal.a)
mammal.sleep()
try:
ic(mammal.__b)
except AttributeError as err:
ic(err)
try:
mammal.__eat()
except AttributeError as err:
ic(err)
14:28:56|> mammal.a: ‘A’
14:28:57|> ‘我困了’
14:28:57|> err: AttributeError(“‘Mammal’ object has no attribute ‘__b’”)
14:28:57|> err: AttributeError(“‘Mammal’ object has no attribute ‘__eat’”)
4.2.1 __init__方法
在类的定义中,默认有一些以__
开头和结尾的特殊方法,这些方法一般是用来处理一些特别的事情,这类方法通常称为魔术方法或魔法方法。__init__
方法就是众多魔法方法中一个非常重要的方法。在类的初始化成对象时会调用这个方法,一般是用来定义一些类的属性,运行一些需要在类初始化时就需要运行的自定义方法。
from icecream import ic
class Animal:
def __init__(self, leg=4):
self.leg = leg
a = Animal()
ic(a.leg)
b = Animal(3)
ic(b.leg)
14:49:39|> a.leg: 4
14:49:39|> b.leg: 3
在上面代码中,因为大部分动物都是4条腿,于是直接将Animal类的leg设置为4,这样在初始化后,a.leg输出的就是默认4。而后又用Animal类初始化了一个对象b,只不过这次传入的leg是3,那么在初始化是调用__init__方法后,输出b.leg就是3了。
4.2.2 super方法
通常子类可以直接调用父类中的方法,如果子类和父类同时都有__init__方法需要定义一些初始化的属性,那么在子类中直接调用__init__方法传入参数显然是不行的。
from icecream import ic
class Animal:
def __init__(self, leg=4):
self.leg = leg
self.type = '双足动物' if self.leg == 2 else '非双足动物'
class Mammal(Animal):
def __init__(self, leg):
self.leg = leg
a = Animal()
ic(a.leg)
ic(a.type)
m = Mammal(leg=2)
ic(m.leg)
ic(m.type)
15:11:48|> a.leg: 4
15:11:48|> a.type: ‘非双足动物’
15:11:48|> m.leg: 2
Traceback (most recent call last):
File “E:\t3.py”, line 21, in
ic(m.type)
AttributeError: ‘Mammal’ object has no attribute ‘type’
我们看到,虽然Mammal类继承了Animal类,但是无法调用Animal类的self.type属性。这是因为初始化后仅运行了Mammal类中的__init__方法而未运行Animal类中的__init__方法导致的。
要想达到传入参数同时被子类和父类初始化引入,则只需要稍微修改一下代码,在子类初始化方法__init__中调用父类的__init__并传入相应的参数即可:
from icecream import ic
class Animal:
def __init__(self, leg=4):
self.leg = leg
self.type = '双足动物' if self.leg == 2 else '非双足动物'
class Mammal(Animal):
def __init__(self, leg):
super().__init__(leg)
a = Animal()
ic(a.leg)
ic(a.type)
m = Mammal(leg=2)
ic(m.leg)
ic(m.type)
15:16:38|> a.leg: 4
15:16:39|> a.type: ‘非双足动物’
15:16:39|> m.leg: 2
15:16:39|> m.type: ‘双足动物’
4.2.3 issubclass (x, A_tuple)、isinstance(x, A_tuple)方法
这2个方法返回x
是派生自另一个类还是同一个类。A_tuple可以是一个类也可以是包含多个类的tuple。如果是tuple,则:
issubclass(x, (A, B, …))等价于:isinstance(x, A) or isinstance(x, B)…
isinstance(x, (A, B, …))等价于:isinstance(x, A) or isinstance(x, B)…
这2个方法区别在于第一个参数x
,对于issubclass方法,第一个参数x
必须是类,而isinstance则必须是对象。文章来源:https://www.toymoban.com/news/detail-551352.html
from icecream import ic
class Animal:
...
class Mammal(Animal):
...
class Bird:
...
class Person(Mammal):
...
a = Animal()
m = Mammal()
b = Bird()
p = Person()
ic(issubclass(m.__class__, a.__class__))
ic(issubclass(m.__class__, b.__class__))
ic(isinstance(p.__class__, a.__class__))
ic(isinstance(p, p.__class__))
15:36:24|> issubclass(m.class, a.class): True
15:36:24|> issubclass(m.class, b.class): False
15:36:24|> isinstance(p.class, a.class): False
15:36:24|> isinstance(p, p.class): True文章来源地址https://www.toymoban.com/news/detail-551352.html
到了这里,关于[Python] 类的继承的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!