1:面向对象的三大特征:
- 1:封装:确保对象中数据的安全(君子协定)
- 2:继承:保证了对象的扩展性(子承父业)
- 3:多态:保证了程序的灵活性(一个按键,多个功能)
2:多态:
- 1:一个对象的多种形态,一种单接口的形式
- 2:一个类所延伸的多种形态
- 3:调用时的多种形态,多用于继承关系
2.1:鸭子类型:
- “当看到一只鸟走起来像鸭子、游泳起来像鸭子、叫起来也像鸭子,那么这只鸟就可以被称为鸭子。”
- 在动态的语言中,只关心对象的行为,不关心对象的类型
2.2:python中多态的特点:
- 1、只关心对象的实例方法是否同名,不关心对象所属的类型;
- 2、对象所属的类之间,继承关系可有可无;
- 3、多态的好处可以增加代码的外部调用灵活度,让代码更加通用,兼容性比较强;
- 4、多态是调用方法的技巧,不会影响到类的内部设计。
2.3:多态的作用
- 节省内存的开支
- 可以运用一个函数来满足调用任意一个对象的方法,可以实现一个函数调用多个类的方法或属性
2.4:多态的常用场合
- 多用于有继承关系的类
- 可以使用一个函数来调用父类重名的函数
3:属性和方法
- 属性:在类里面的变量
- 方法:在类里面的函数
3.1属性:
- 属性的分类:
1:类属性
2:实例属性
3.1.1:类属性
- 类属性的定义:直接定义在类里面,方法之外的属性
# 定义一个类,包含了name、age、color三个类属性
class Dog(object):
name = "哈士奇"
- 类属性的调用:既可以使用类对象来调用,也可以使用实例实例对象来调用
语法:
# 使用类来调用类属性(语法格式:类名.属性名)
print(Dog.name)
# 使用实例对象来调用类属性(语法格式:实例对象名.属性名)
dog_1 = Dog()
print(dog_1.name)
-------------------------------------------------------------
输出:
"哈士奇"
"哈士奇"
- 类属性的修改:只能通过类对象来修改,不能通过实例对象来修改
# 使用实例对象来修改类属性的值
dog_1 = Dog()
dog_1.name = "泰迪"
print(Dog.name)
print(dog_1,name)
-------------------------------------------------
输出:
"哈士奇"
"泰迪"
==========================================
使用类对象来修改类属性的值
Dog.name = "泰迪"
print(Dog.name)
print(dog_1.name)
--------------------------------------------
输出:
"泰迪"
"泰迪"
======由此可见类属性只能通过类对象来修改,不能通过实力对象来了修改======
- 总结:有上面的代码可知,类属性和实例属性分别放在两个内存的空间中
3.1.2:实例属性:
- 实例属性的定义:通过实例对象添加的属性就是实例属性
# 实例属性的添加(还是遵循上面的类)
dog_1.name = "泰迪"
# 这就是添加了一个实例属性
- 实例属性的访问:实例属性只有实例对象可以访问,类对象不可以访问
- 实例属性的修改:实例属性只有实例对象可以修改,类对象不可以修改
- 注意:__init__构造方法里面的属性是实例属性,并不属于类属性,具体可以思考一下__init__方法的作用
3.2:方法
- 方法的分类:
1:实例方法
2:类方法
3:静态方法
3.2.1:实例方法
- 实例对象的定义:在类中定义,以self为第一个参数的方法都是实例方法
- 实例方法的调用:实例方法在调用时,Python会将调用对象以self传入
- 可调用的对象:实例方法可以通过实例对象和类对象去调用
1:当通过实例调用时,会自动将当前调用对象作为self传入
2:当通过类调用时,不会自动传递self,我们必须手动传递self
# 定义一个实例方法
calss Dog(object):
def preak(slef):
print("大家好!")
# 通过实例对象来调用实例方法
dog_1 = Dog()
print(dog_1.preak())
---------------------------------------
输出:
"大家好!"
# 通过类对象来调用
print(Dog.preak(dog-1))
-----------------------------------------
输出:
"大家好!"
- 总结:实例方法既可以用实例对象来调用,也可以使用类对象来调用,但是使用类对象来调用的时候要要传入一个实例对象作为参数
3.2.2:类方法
- 类方法的定义:在类的内容以@classmethod 来修饰的方法属性类方法
- 类方法第一个参数是cls 也会自动被传递。cls就是当前的类对象
- 类方法可以通过类对象去调用,也可以通过实例对象调用
3.2.3:类方法与实例方法的区别
- 类方法和实例方法的区别,实例方法的第一个参数是self,类方法的第一个参数是cls
- 实例方法可以用实例对象和类对象来调用,不过实例对象调用的时候不需要传递参数,类对象调用的时候需要传递一个实例对象
- 类方法可以使用实例对象和类对象来调用,并且类对象的调用都不需要传递任何参数
3.2.4:静态方法
- 静态方法的定义:在类中用@staticmethod来修饰的方法属于静态方法
1:本质上是一个函数,可以完成一些事情 - 静态方法不需要指定任何的默认参数,静态方法可以通过类和实例调用
1:调用的方法和类方法的调用一样 - 静态方法,基本上是一个和当前类无关的方法,它只是一个保存到当前类中的函数
1:用来存储一些工具方法 - 静态方法一般都是些工具方法,和当前类无关
实例方法、类方法和静态方法的差别
方法名称 | 方法解释 | 方法的调用 |
---|---|---|
实例方法 | 在类中有self参数的就是实例方法,实例方法的第一个参数为self | 可以通过实例对象调用,也可以通过类对象调用,不过使用类对象调用的话要传入一个实例对象作为参数 |
类方法 | 在类中使用装饰器@classmethed来修饰的方法,就是类方法,类方法的第一个参数为cls | 可以由实例对象调用,也可以由类对象调用,并且调用都不需要传递参数 |
静态方法 | 在类中用@staticmethod来修饰的方法,就是属于静态方法,静态方法没有参数,静态方法只不过是一个功能函数,用来完成某些功能,不会影响类中代码的运行 | 可以由实例对象调用,也可以由类对象调用,并且调用都不需要传递参数 |
4:__new__方法
- 需要使用一个魔法方法:__new__方法
4.1:__new__方法(构造方法)
- 类里面的方法会最先执行__new__里面的代码
- 对象创建的顺序
1.通过__new__()方法创建对象
2.并将对象返回,传给__init__() - 实例化对象的步骤:1:制作一个对象;2:为对象进行初始化操作
4.1.1:__new__方法的特点
- __new__()方法用于制作并返回一个对象
- __new__方法为类的静态方法,即使没有用装饰器
- __new__方法参数中的"cls参数"表示会把当前的类传入到"cls"中
4.2:__new__方法的作用
- 1:可以调用其它类的构造方法,或者直接返回别的类对象,作为本类的实例。如:
class Dog(object):
pass
class Car(object):
def __new__(cls, *args, **kwargs):
return object.__new__(Dog)
print(Car())
---------------------------------
- 返回的就是Dog的对象
- 2:在自身实例化的时候调用
- 3:在内存中为对象分配空间
- 4:返回对象的引用
- 5:可以实现单例模式
类的实例化:其实就是odject类里面的__new__方法创建出来的,而在类里面写入__new__方法其实就是在重载odject类类里面的__new__方法,所以说__new__方法可以管理控制对象的生成过程
4.3:__new__方法的用处
- 使用__new__方法制作对象的时候需要借助最基本的object类
- 可以用一个类里面的__new__方法方法来创建另一个类里面的对象,但是这种需求很少,所以不经常使用,仅供娱乐
4.4:__new__方法的其它特性
- 参数:cls参数用来接收当前的类,其它的情况根据实例化参数决定
- 返回值:可有可无
- 注意事项:__new__方法和__init__方法除了第一个参数不同之外,其余的参数都相同
4.5:注意
- 在创建对象时,一定要将对象返回,才会自动触发__init__()方法
- __init__()方法当中的self,实际上就是__new__返回的实例,也就是该对象
4.6:__new__方法与__init__方法的区别
1: __init__实例方法,__new__静态方法
2:__init__在对象创建后自动调用,__new__创建对象的方法
3:__init__方法为__new__创建的对象添加成员
5:单例模式
5.1单例模式介绍
1:单例模式是一种常用的软件设计模式。也就是说该类只包含一个实例。
2:通过单例模式可以保证系统中一个类只有一个实例,而且该实例易于外界访问,从而方便对实例个数的控制并节约系统资源。如果希望在系统中某个类的对象只能存在一个,单例模式是最好的解决方案。
3:通常应用在一些资源管理器中,比如日志记录等。
5.2单例模式实现
思路:
• 当对象不存在时,创建对象
• 当对象存在时,永远返回当前已经创建对象
5.3:代码演示
class single(object):
__isinstance = None
def __new__(cls, *args, **kwargs):
if cls.__isinstance is None:
cls.__isinstance = super().__new__(cls)
return cls.__isinstance
else:
return cls.__isinstance
a = single()
b = single()
print(id(a))
print(id(b))
- 其中super()方法用于返回实例的方法,也就是用odject类来创建一个single的实例对象
6:模块
6.1:模块简介
- 模块化指将一个完整的程序分解成一个个的小模块
- 通过将模块组合,来搭建出一个完整的程序
- 模块化的优点
• 方便开发
• 方便维护
• 模块可以复用
6.2:模块的创建
- 1:在Python当中一个py文件就是一个模块
- 2:在一个模块中引入外部模块 import 模块名(模块名就是py文件)
- 3:可以引入同一个模块多次,但是模块的实例只会创建一次
- 4:import 模块名 as 模块别名
- 5:在一个模块内部都有一个__name__。通过它我们可以获取模块的名字
- 6:如果py文件直接运行时,那么__name__默认等于字符串’main’。__name__属性值为__main__的模块是主模块。一个程序中只有一个主模块
6.3:模块的使用
- 1:访问模块中的变量
- 语法:模块名.变量名
- 2:访问模块中的函数
- 语法:模块名.函数名
- 3:访问模块中的对象
- 语法:模块名.对象名
- 4:我们也可以引入模块中部分内容
- 语法:from 模块名 import 变量,变量…
- 5:其它引入方式
- 语法:from 模块名 import 变量 as 别名