上一关我们为大家介绍了函数,我们一起来回顾下上一关的内容:

image.png

今天呢,我们将为大家介绍类和对象,类和对象是面向对象编程的核心概念。

我们一起来通过百鸟朝凤的故事认识 Python 中的类和对象:

一天,伏羲巡视到西山桐林,只见金、木、风、火、土五行之精,纷纷飘落在梧桐树上。顿时,仙乐飘飘,香风习习。又见瑞气千条,霞光万道。天空彩屏开处,祥云托着两只美丽的大鸟,翩翩降落在那棵梧桐树上,其余诸鸟纷纷飞集在各处树上,朝着两只美丽的大鸟齐鸣。伏羲见到如此奇异现象,忙召来辅佐他的木神句芒问个究竟。句芒笑着对伏羲道:“这两只最大的鸟,就是凤凰呀!”

故事中,当凤凰出现的时候,所有鸟都朝着凤凰齐鸣,说明了凤凰在鸟类当中的地位。而凤凰之所以能够吸引到鸟,而不是其他动物,也是因为凤凰和其余鸟,同属于鸟这个大类里面,应了“物以类聚”这句话。我们生活中,会将具有一些共性特征的生物或者是物体划分为一类,比如鸟类、鱼类、厨房用品、办公用品等等。Python 中的类,和我们生活的“物以类聚”类似,都是包含了这一类别内都具备的一些特征。Python 中的类是用来描述具有相同的属性和方法的对象的集合,它定义了该集合中每个对象所共有的属性和方法。类是抽象的模板,比如说鸟类,我们在提到鸟类的时候,并不知道具体是哪一种鸟;对象是对类进行具象的实例化,比如说凤凰、鹦鹉、麻雀等,他们都是鸟的一种,提到凤凰、鹦鹉、麻雀的时候,我们会在脑海中勾勒出具体的形象;而在类中,我们也可以对凤凰、鹦鹉、麻雀这些鸟进行一些属性的定义,比如羽毛颜色、尺寸大小等等。下面呢,我们分别为大家介绍 Python 中的类与对象,首先我们来看,类的创建:

# 1 类

# 1.1 创建类

我们一起来看下类是如何创建的:

image.png

类的定义以关键字 class 开头,后面紧跟类名和冒号,下面跟着是类的主体部分,代码以缩进标识。

我们一起来看下方语句:

#创建类Bird
class Bird:
    #对象初始化语句
    def __init__(self, n, c, s):
        self.name = n
        self.color = c
        self.size = s
    
    #定义方法get_description,参数为self,自动传入
    def get_description(self):
        description = f'{self.name} {self.color} {self.size} '
        print(description)
1
2
3
4
5
6
7
8
9
10
11
12

我们创建了一个类 Bird,并定义了类 Bird 的两种方法(类中的函数称作方法) __init__( )get_description( ),这两个方法是所有属于类 Bird 的对象共有的方法,下面我们一起看下 Python 中初始化属性的方法 __init__( )

# 1.2 __init__() 方法

类中的函数称作方法,__init__() 是一个特殊的方法,每当我们实例化一个对象时,这个方法都会自动执行。方法名的开头为两个下划线,结尾同样为两个下划线,这种命名的习惯主要是为了区分 Python 默认的方法名和我们自己定义的方法名。

def __init__(self, n, c, s): 语句中,参数 self 表示对象自身,代表实例化对象的引用。参数n, c, s则表示对象的属性,在我们创建的类 Bird 中就是表示,每一种鸟的具象化特征,比如鹦鹉、绿色、中等大小,因此 __init__() 方法的作用是为对象的属性赋值。

__init__() 的参数规则如下图: image.png

参数 self 是必须的,并且要位于其他参数的前面。在方法的定义中,之所以要必须包含 self 参数,是因为当实例化对象时,会自动调用 __init__() 方法,并且自动传入参数 self。每个方法都可以包含一个会自动传入的参数 self,这个参数是实例化对象的引用。这样方法便可以访问对象的属性和方法。在实例化对象时,由于 self 参数自动传入的,所以只需要传入其他参数的值。

我们再来一起看下 __init__() 函数体中的语句:

    def __init__(self, n, c, s):
    #对象初始化语句
        self.name = n
        self.color = c
        self.size = s
1
2
3
4
5

__init__() 函数体中,赋值号左边的参数带有 self 前缀,带有 self 前缀的变量对于类中的每个方法来说都是可用的,而且也可以通过实例化的对象来访问这些变量。self.name = n 将参数 n 赋值给 namename 便是实例化出来的对象的属性;self.color = c 将参数 c 赋值给 colorcolor便是实例化出来的对象的属性;self.size = s 将参数 s 赋值给 sizesize便是实例化出来的对象的属性。

我们继续来看类 Bird 中定义的方法 get_description() 语句:

    def get_description(self):
    #定义方法get_description,参数为self,自动传入
        description = f'{self.name} {self.color} {self.size} '
        print(description)
1
2
3
4

这个方法由于不需要传入额外的信息,所以只要传入 self 参数,函数中定义了变量 description 和打印description 的语句,当调用 get_description() 方法时,执行打印语句。

我们继续一起来看对象:

# 2 对象

类是用来描述具有相同的属性和方法的对象的集合,它定义了该集合中每个对象所共有的属性和方法。类是抽象的,对象是对类进行具象的实例化。我们从刚刚的例子中,也了解到了,类是鸟类,对象是具体的某一种鸟,比如凤凰、麻雀、鹦鹉等等,下面我们就一起来看下如何通过 Python 语句来实现对象的实例化。

# 2.1 实例化对象

我们先来看下方语句:

#创建类Bird
class Bird:

    #对象初始化语句
    def __init__(self, n, c, s):
        self.name = n
        self.color = c
        self.size = s

     #定义方法get_description,参数为self,自动传入
    def get_description(self):
        description = f'{self.name} {self.color} {self.size} '
        print(description)

#实例化对象my_bird,为my_bird赋予属性'鹦鹉', '绿色', '中等大小'
my_bird = Bird('鹦鹉', '绿色', '中等大小')
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16

在语句中,我们添加了一句 my_bird = Bird('鹦鹉', '绿色', '中等大小') 会实例化类 Bird 的一个对象 my_bird,在实例化的过程中,会调用 __init__() 方法,将值'鹦鹉'传递给参数 n,值'绿色'传递给参数 c,值'中等大小'传递给参数 s

运行上述语句,我们看并没有结果的输出,因为只完成了类的定义,以及其中一个对象的实例化,并没有去调用类中定义的方法,也没有访问对象的属性。

下面就看一下对象的属性访问。

# 2.2 访问属性

访问属性的语法为:对象名.属性名

我们看下方语句:

class Bird:

    def __init__(self, n, c, s):
        self.name = n
        self.color = c
        self.size = s

    def get_description(self):
        description = f'{self.name} {self.color} {self.size} '
        print(description)


my_bird = Bird('鹦鹉', '绿色', '中等大小')
print(f"My bird's name is {my_bird.name}")
print(f"My bird's color is {my_bird.color}")
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15

在上面的语句中,我们通过 my_bird.namemy_bird.color 访问对象 my_bird 的属性 namecolor。我们继续来看如何实现方法的访问。

# 2.3 访问方法

访问方法的语法规则和访问属性是类似的,都是用 . 符号来实现:对象名.方法名

我们来看下方语句:

class Bird:
    def __init__(self, n, c, s):
        self.name = n
        self.color = c
        self.size = s

    def get_description(self):
        description = f'{self.name} {self.color} {self.size} '
        print(description)


my_bird = Bird('鹦鹉', '绿色', '中等大小')
my_bird.get_description()
1
2
3
4
5
6
7
8
9
10
11
12
13

我们看到通过访问方法语句 my_bird.get_description(),成功执行方法 get_description() 中的打印语句。

# 2.4 实例化多个对象

我们还可以同时实例化多个对象:

class Bird:
    def __init__(self, n, c, s):
        self.name = n
        self.color = c
        self.size = s

    def get_description(self):
        description = f'{self.name} {self.color} {self.size} '
        print(description)


my_bird = Bird('鹦鹉', '绿色', '中等大小')
your_bird = Bird('麻雀', '灰色', '小小一只')
print(f"My bird's name is {my_bird.name}")
my_bird.get_description()
print(f"Your bird's name is {your_bird.name}")
your_bird.get_description()
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17

我们实例化了两个对象 my_birdyour_bird。在实际应用中,可以用同样的方法实例化多个对象哟!

# 2.5 为属性设置默认值

我们也可以为属性设置默认值,一起看下方语句:

class Bird:
    def __init__(self, n, c, s):
        self.name = n
        self.color = c
        self.size = s
         #设置属性age的默认值为1
        self.age = 1
       

    def get_description(self):
        description = f'{self.name} {self.color} {self.size} '
        print(description)

    #定义获取属性age的方法
    def get_age(self):
        print(f"This bird is {self.age} ")


my_bird = Bird('鹦鹉', '绿色', '中等大小')
print(f"My bird's name is {my_bird.name}")
my_bird.get_description()
my_bird.get_age()
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22

我们在上述代码中添加了一个属性 age,并且将默认值设置成 1。并且添加一个方法 get_age() 用于获取属性 age 的值。

# 2.6 直接改变属性的值

我们也可以直接修改属性值,语句为:对象名.属性名 = 值,我们一起看下方语句:

class Bird:
    def __init__(self, n, c, s):
        self.name = n
        self.color = c
        self.size = s
        self.age = 1

    def get_description(self):
        description = f'{self.name} {self.color} {self.size} '
        print(description)

    def get_age(self):
        print(f"This bird is {self.age} ")


my_bird = Bird('鹦鹉', '绿色', '中等大小')
my_bird.age = 3
my_bird.get_age()
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18

# 2.7 通过方法改变属性的值

我们也可以通过方法来改变属性的值:

class Bird:
    def __init__(self, n, c, s):
        self.name = n
        self.color = c
        self.size = s
        self.age = 1

    def get_description(self):
        description = f'{self.name} {self.color} {self.size} '
        print(description)

    def get_age(self):
        print(f"This bird is {self.age} ")

    def update_age(self, a):
        self.age = a


my_bird = Bird('鹦鹉', '绿色', '中等大小')
my_bird.update_age(5)
my_bird.get_age()
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21

在上述语句中,我们定义了一个改变属性值的方法 update_age(),通过调用 update_age() 来改变属性的值。

# 3 继承

在创建类时,不必每次都从零开始,假设我们想要创建的新类和已经创建过的类之间有一些共同的属性和方法,我们就可以从某个现有的类继承,新类称为子类,被继承的类称为父类。继承时,子类会获取父类的所有属性和方法,并且子类还可以定义自己的属性和方法。

子类的语法规则是:class 新类名(父类名),比如 class Penguin(Bird) 就表示一个子类,父类为 Bird

# 3.1 子类的 __init__() 方法

在实例化子类的对象时,首先要为父类中的属性赋值,对父类属性的赋值可以使用父类的 __init__() 方法。

class Bird:
    def __init__(self, n, c, s):
        self.name = n
        self.color = c
        self.size = s
        self.age = 1

    def get_description(self):
        description = f'{self.name} {self.color} {self.size} '
        print(description)

    def get_age(self):
        print(f"This bird is {self.age} ")

    def update_age(self, a):
        self.age = a


class Penguin(Bird):
    def __init__(self, n, c, s):
        super().__init__(n, c, s)


my_bird = Penguin('企鹅', '黑白', '大')
my_bird.get_description()
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25

在上面的例子中,定义了一个新类 Penguin,新类继承自 Bird。在子类  Penguin__init__() 方法中调用父类 Bird__init__() 方法对父类中的属性进行赋值。语句中的 super() 函数是用于调用父类的一个方法。

# 3.2 定义子类的属性和方法

我们也可以在子类中定义属性和方法,语法规则和在类中定义属性和方法的规则一致,我们看下方语句:

class Bird:
    def __init__(self, n, c, s):
        self.name = n
        self.color = c
        self.size = s
        self.age = 1

    def get_description(self):
        description = f'{self.name} {self.color} {self.size} '
        print(description)

    def get_age(self):
        print(f"This bird is {self.age} ")

    def update_age(self, a):
        self.age = a


class Penguin(Bird):
    def __init__(self, n, c, s):
        super().__init__(n, c, s)
        self.swimming_distance = 100

    def get_swimming_distance(self):
        print(f"企鹅可以游 {self.swimming_distance} 米.")


my_bird = Penguin('企鹅', '黑白', '大')
my_bird.get_description()
my_bird.get_swimming_distance()
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30

为子类添加了属性 swimming_distance 和方法 get_swimming_distance(),通过访问属性和方法打印出相应的结果。

# 4 总结

image.png

# 5 练习题

定义一个表示鱼的类,并定义它的继承类海鱼。

更新于: 12/30/2021, 2:46:39 AM