找往期文章包括但不限于本期文章中不懂的知识点:
个人主页:我要学编程(ಥ_ಥ)-CSDN博客
所属专栏: Python
目录
前言介绍
类的定义和使用
动态绑定属性与方法
前言介绍
Python 是一门既支持面向过程,又支持面向对象的编程语言。如果有小伙伴学过C语言 和 Java的话,就会发现 Python 是类似于两者的结合体,C语言是支持纯面向过程的,而Java是支持纯面向过程的。
前面我们都是在学习面向过程,今天我们就要来学习面向对象了。两者的区别就在于对同一件事情的处理角度不同。例如,同样是去吃饭,面向对象的角度,就是关注:人、饭馆、菜 这些对象;而面向过程的角度,就会关注:怎么去?怎么点菜?怎么吃饭?这些过程是如何去实现的。下面我们就来看类的定义与使用。
类的定义和使用
在Python中一切皆是对象。例如,田园犬、宠物犬等都是属于对象,它们都有自己的名字、年龄、性别等,这些我们都统称为对象的属性。我们之前在学习函数的时候,了解了函数的作用之一:对需要重复调用的代码进行封装。而这里的对象的很多属性也都是会重复出现的,因此我们把这些重复出现的属性封装成类似函数一样的,就统称为"类",当然类中不只是属性,还有一种共有的行为也被封装为了方法。类就是用来描述对象的,是创建对象的模版。
语法:
class 类名(): ... // 属性 ... // 方法
代码演示:
# Dog 是类名,通常首字母大写,后面跟着"()"class Dog(): # 类中存在 属性 与 行为(被封装成方法) # 下面的 name 与 age 都是属性 —> 类属性 name='' age=0 # 在 __init__方法中定义的是属于实例属性 def __init__(self): self.sex = '♂'
先来解释几个名词的含义吧。
1、封装:隐藏内部的实现细节,对外提供接口,这是属于面向对象编程的三大特性之一。例如,我们生活中所使用的USB接口,我们想要通过 U盘 传输数据时,不必了解这个原理是如何实现的,只需要提供一个接口给我,插入U盘就行。
2、类属性:也被称为静态属性或者静态变量,这是一种属性,是类独有的,而不是对象的,每个对象都可以去访问它,但是访问的都是同一份。
3、实例属性:也被称为实例变量,这也是一种属性,是对象独有的,每个对象去访问实例属性时,是访问它自己的,每一个对象都有一份。
注意:当类属性与实例属性一致时,优先访问实例属性,因为这是在对象内部寻找的,而类属性是需要在类中去寻找的。
类的出现就是为了更好的描述对象,那么怎么去创建对象呢?
语法:
# [参数1, 参数2, ...] 可省略对象名 = 类名([参数1, 参数2, ...])
代码演示:
# 对象可以创建任意多个dog1 = Dog()dog2 = Dog()dog3 = Dog()
() 中的参数是根据我们定义的 __init__方法中的参数来传输的,如果__init__方法中,没有参数,就不需要传输,如果有参数有需要传输。
注意:
1、类中的函数,我们都是称作方法。
2、通过类去创建对象的过程,我们称为 类的实例化,将一个模版,变成了一个真实存在的对象。
上面学习了一个类的编写与类的实例化,我们来看完整的类,应该是由几部分组成。
我们也可以通过代码来演示一下:
class Dog(): # 类属性 sort='中华田园犬' # 初始化对象的方法(构造方法)——>每个对象在创建时,都会调用它 # 如果这里的name与age不使用"self."的话,就是一个局部变量了,而不再是实例变量 def __init__(self, name, age): # 实例属性 self.name = name self.age = age # 静态方法 @staticmethod def bark(): print('这是一个静态方法,里面不能出现与实例相关的属性或者方法') # 类方法 @classmethod def sort(cls): print('这是一个类方法,里面也不能出现与实例相关的属性或者方法') # 实例方法 def roll(self): print(f'{self.name}正在地上打滚~')# 实例化一个对象# 实例属性与实例方法是通过对象去调用的dog = Dog('大白', 5) # 需要传入参数构造对象(__init__)dog.roll()# 类属性、类方法、静态方法等都是通过类名去调用的Dog.bark()Dog.sort()
运行结果:
注意:
1、虽然类方法 与 静态方法都是需要通过类名来调用的,但不意味着两者的用途也是一致的。类方法通常用来操作与类相关的属性;而静态方法一般是起到函数的作用,用来执行什么样的功能。
2、类方法 与 静态方法虽然表面上说是只能通过 类名 来调用,但实际上也是可以方法名来调用的。如下所示:
动态绑定属性与方法
当我们实例出多个对象之后,可能某些对象需要一些特殊的属性,而这些属性是不能存在于模版(类)中的,因此,我们只能通过动态绑定来修改对象的属性或者方法。
在正式学习之前,我们先来看一个小故事:相比大家应该都看过《无间道》,这里面的刘建明(下面用 刘 来代替) 与 陈永仁(下面用 陈 来代替) 分别是 黑社会安插在警方 与 警方安插在黑社会的卧底。假设 警察 与 黑社会 就是两个类,而 陈 与 刘 就是两个类分别实例化出来的对象,但是后面双方高层都决定要对方的潜入敌方阵营,因此这里就需要更改身份(程序运行的过程中,而不是创建的过程中,原本的身份早已注定),这里就需要用到动态绑定。
代码演示:
class Police(): # 类属性 id = '人民警察' # 实例方法 def __init__(self, name, age, sex): self.name = name self.age = age self.sex = sex def identity(cls): print(f'我是{cls.id}')class Underworld(): id = '黑社会' # 实例方法 def __init__(self, name, age, sex): self.name = name self.age = age self.sex = sex def identity(cls): print(f'我是{cls.id}')def deepIdentify(deepId): print(f'我是{deepId}')chen = Police('陈永仁', 20, '男')liu = Underworld('刘建明', 20, '男')huang = Police('黄警官', 32, '男')han = Underworld('韩琛', 34, '男')print('故事背景:')print('香港警方为了剿灭黑社会团体,于是安插了陈永仁在黑社会当卧底,' '而韩琛为了存活,则派遣刘建明等人潜入警方卧底')print('命运的齿轮开始转动,两者的身份开始转换:')print('='*30)chen.id = '黑社会'chen.deepId = '人民警察' # 动态绑定-属性chen.deepIdentify = deepIdentify # 动态绑定-方法liu.id = '人民警察'liu.deepId = '黑社会' # 动态绑定-属性liu.deepIdentify = deepIdentify # 动态绑定-方法print(f'陈永仁的表面身份{chen.id},但其真实身份是{chen.deepId}')print(f'刘建明的表面身份{liu.id},但其真实身份是{liu.deepId}')print('='*30)print(f'当陈永仁遇到{han.name}时,他会微笑着说出: ',end='')chen.identity()print(f'当陈永仁遇到{huang.name}时,他会情不自禁地说出: ',end='')chen.deepIdentify (chen.deepId)print('并时刻提醒自己不要堕落,要牢记初心与使用')print('='*30)print(f'当刘建明遇到{huang.name}时,他会微笑着说出: ',end='')liu.identity()print(f'当刘建明遇到{han.name}时,他会咬牙切齿地说出: ',end='')liu.deepIdentify (liu.deepId)print(f'并时刻想着杀了{han.name},过着自己现在的逍遥快乐的小日子')
运行结果:
注意:
1、动态绑定修改的是对象的属性 与 方法,并不会影响未修改的对象,即不会对类产生效果。
2、动态绑定的语法:
# 动态绑定修改属性对象名.属性 = 属性值# 动态绑定修改实例方法对象名.调用时想要用到方法名 = 实际的方法名# 调用修改的方法对象名.调用时想要用到方法名([参数列表])
如果《无间道1》最后的结局是 黄警官一方大获全胜,而韩琛等人均被绳之以法的话,后面就需要恢复 刘 与 陈的真实身份,原来的假身份应当被彻底消除,相当于是删除动态绑定的方法与属性。
语法:
del 对象名.属性del 对象名.方法
代码演示:
print('修改版剧情(纯写作需要,不喜勿喷):')print('最终,刘建明良心发现,主动自首,给警方提供了韩琛等人的违法犯罪行为的证据,' '警方立即出动,将其逮捕归案,陈永仁也成功获得了高级荣誉称号!')print('接下来,就是修改 刘建明 与 陈永仁的相关档案了: ')chen.id = '人民警察'del chen.deepIddel chen.deepIdentifyliu.id = '黑社会'del liu.deepIddel liu.deepIdentifyprint(f'陈永仁的档案:{chen.name,chen.age,chen.sex,chen.id}')print(f'刘建明的档案:{liu.name,liu.age,liu.sex,liu.id}')print(liu.deepId) # errorprint(chen.deepId) # error
运行结果:
既然属性与方法可以删除,那么对象 与 类是否也可以删除呢?确实如此,对象与方法也是可以删除的。
语法也是类似的,这里就直接给出代码了:
好啦!本期 初始Python篇(10)—— 初识 类与对象 的学习之旅 就到此结束啦!我们下一期再一起学习吧!