目录
1.面向对象
面向过程就是分析出解决问题所需要的步骤,然后用函数把这些步骤一步一步实现,使用的时候一个一个依次调用就可以了。
Python中万事万物皆对象,而面向对象的三大特性:封装、继承和多态。
常见的面向对象编程语言:Java / C++ / Python等等。
2.类的定义
Python 中定义一个类使用 class 关键字实现,其基本语法格式如下:
class 类名: 多个(≥0)类属性... 多个(≥0)类方法... #Python 类中属性和方法所在的位置是任意的,即它们之间并没有固定的前后次序。
和变量名一样,类名本质上就是一个标识符,因此我们在给类起名字时,必须让其符合 Python 的语法。
有读者可能会问,用 a、b、c 作为类的类名可以吗?
从 Python 语法上讲,是完全没有问题的,但作为一名合格的程序员,我们必须还要考虑程序的可读性。
因此,在给类起名字时,最好使用能代表该类功能的单词。
class Dog: name: str = "小黑" age: int = 2
2.1实例化对象
2.2类变量
通过类对象来调用所属类中的类变量:(此方式不推荐使用) # 实例化对象 d1 = Dog() # 获取对象中的属性 print(f"name={d1.name},age={d1.age}") # 修改对象中的属性 d1.name="小黑" d1.gender="公" print(f"name={d1.name},gender={d1.gender}")
类变量指的是在类中,但在各个类方法外定义的变量。
所有类的实例化对象都同时共享类变量: class Dog: name: str = "小黑" # 类的属性 age: int = 2 # 实例化 dog = Dog() dog2 = Dog() # 以下访问的是类属性 print(Dog.name) print(dog.name) print(dog2.name) # 向dog实例添加name属性 dog.name = "小花" print(dog.name) dog2.name = "小白" # 向Dog类添加sex类属性 Dog.sex = '公' print(dog.sex)
#通过类名调用类变量和修改类变量的值: # 使用类名直接调用 print(f"name={Dog.name},type={Dog.type},age={Dog.age}") # 修改类变量的值 Dog.name="钱多多" print(Dog.name)
注意:通过类对象是无法修改类变量的。通过类对象对类变量赋值,其本质将不再是修改类变量的值,而是在给该对象定义新的实例变量 。
3.魔法函数
Python 类中,凡是以双下划线 "" 开头和结尾命名的成员(属性和方法),都被称为类的特殊成员(特殊属性和特殊方法)。例如,类的 init__(self) 构造方法就是典型的特殊方法。
3.1init()构造函数
在创建类时,我们可以手动添加一个 __init__()
方法,该方法是一个特殊的类实例方法,称为构造方法(或构造函数)。
Python类中,手动添加构造方法的语法格式如下:
def __init__(self,...): 代码块
""" init函数 1.self:名称可以任意,位于方法第一个参数,代表当前对象 2.当实例化类时,init方法会自动调用 3.python中没有重载,参数使用默认值 """ class Car: # 类变量:所有实例共享 total_count: int = 0 def __init__(self, brand: str, color: str): # 实例变量,动态向当前对象self中添加brand,color实例变量 self.brand = brand self.color = color Car.total_count += 1 c1 = Car('比亚迪', '棕色') c2 = Car('大众', '红色') print(c1.brand, c1.color) print(c2.brand, c2.color) print(Car.total_count)
3.2__str__()
重载父类object中的
__str__()
用于将值转化为字符串形式:""" __str__:默认返回 类的全路径,内存地址: 特点:print时会自动调用 """ class Dog: def __str__(self): return f"name={self.name},age={self.age},sex={self.sex}"
3.3__call__()
""" __call__:类实例对象可以像调用普通函数那样调用call函数 """ class Dog: # 定义__call__方法 def __call__(self,name,age): print("调用__call__()方法",name,age) d1 = Dog() d1("小花",2)
3.4__new__()
"""
1.new和init都会被自动调用
2.new创建对象,init使用new创建的对象进行初始化属性
cls:代表当前类,通过它访问类的成员
"""
class AppConfig(object):
ac = None
def __new__(cls, *args, **kwargs):
print("new...")
if not cls.ac:
cls.ac = object.__new__(cls, *args, **kwargs)
return cls.ac
def __init__(self):
print('init...')
a1 = AppConfig()
a2 = AppConfig()
print(a1 == a2)
更多内容,请查看 Python中的魔法函数。
4.三大特性
封装、继承、多态。
4.1封装
封装:将属性和实现细节隐藏,提供可访问的接口。
类方法
Python 类方法和实例方法相似,它最少也要包含一个参数,和实例方法最大的不同在于,类方法需要使用
@classmethod
修饰符进行修饰,例如:# 类方法 cls代表当前类,通过cls调用类的成员 class Dog: # 类方法 @classmethod def info(cls): print(cls)
静态方法
静态方法,其实就是我们学过的函数,和函数唯一的区别是,静态方法定义在类这个空间(类命名空间)中,而函数则定义在程序所在的空间(全局命名空间)中。
静态方法需要使用
@staticmethod
修饰,例如:# 静态方法 类的静态方法中无法调用类任何属性的类方法 @staticmethod def say(): print("静态方法被调用了...")
4.2继承
Python 中,实现继承的类称为子类,被继承的类称为父类(也可称为基类、超类)。
子类继承父类时,只需在定义子类时,将父类(可以是多个)放在子类之后的圆括号里即可。语法格式如下:
class 类名(父类1, 父类2, ...): #类定义部分
class Father(object):
height = 180
money = 100
def work(self):
print("会工作")
pass
class Mother(object):
fact = '漂亮'
money = 90
def cook(self):
print("会做法")
pass
class Son(Father, Mother):
pass
son = Son()
son.work()
son.cook()
print(son.height)
print(son.money)
#同时继承 Father类和 Mother类时,Father类在前,当属性和方法重复时,越往前优先级越高。
#查看继承关系
print(Son.__bases__)
print(Son.__mro__) # mor 决定查找方法的路径
4.3多态
# 多态
class Animal(object):
def play(self):
pass
class Tiger(Animal):
def play(self):
print("正在表演老虎后脚直立行走")
class Lion(Animal):
def play(self):
print("正在表演狮子跳火圈")
class Person(object):
def show(self, a: Animal): # 声明父类类型,传入子类实例
print("动物表演开始了")
a.play() # 多态
p = Person()
a = Animal()
t = Tiger()
l = Lion()
p.show(t)
5.__slots__
每个类都有实例属性。默认情况下Python⽤⼀个字典来保存⼀个对象的实例属性。所以我们在可以在运⾏时去设置任意的新属性。
Python 提供了
__slots__
属性,通过它可以避免用户频繁的给实例对象动态地添加属性或方法。# __slots__ class Dog(object): __slots__ = ["name","age"] def __init__(self,name,age): print("实例化") self.name = name self.age = age dog = Dog('小猴','12')
5.1类装饰器
类装饰器在内部的装饰函数是用__call__()
方法实现的。
class Logger(object):
def __init__(self, path='out.txt'):
self.path = path
def __call__(self, func):
def inner():
log = func.__name__ + "执行"
with open(self.path, 'a') as opened_file:
opened_file.write(log + '\n')
self.notify()
return inner
def notify(self):
pass
@Logger()
def hello():
pass
hello()
#@Logger 在这里的作用实际就是实例化一个fun对象(fun=Logger(fun))
6.思维导图
----------------------------------------------------------------------------------------♥-------------------------------------------------------------------------------------
往期Python内容: