*第 1 篇 · 心法:面向对象(上)· 以万物为模,以众生为象

编程如造物,类为模,对象为器。
上篇传授「封装」与「魔法方法」之秘,让你从「写代码」升级为「造世界」。
从此,世间万物皆可对象化。
1. 类和对象
1.1 什么是类和对象
| 类 | 抽象的模板 | 做月饼的模具 |
| 对象 | 模板的具体实现 | 模具扣出来的月饼 |
模具是类,月饼是对象。一个模具可以产出 N 个月饼,所有月饼的特征都是类给的。比如模具的花样是"福",扣出来的月饼花样一定是"福"。
1.2 定义类和实例化对象
# 定义类(类是抽象的模板)
class Car:
# 定义方法
def run(self):
print("我是个汽车,跑起来了")
# 实例化对象(对象是抽象模板的具体实现)
my_car = Car() # Python 不需要 new 关键字
my_car.run()
# 可以创建多个实例
my_car1 = Car()
my_car1.run()
1.3 查看对象内存地址
# id() 可以查看对象在内存中的地址(十进制)
print(id(my_car))
2. self 关键字
2.1 self 的作用
- self 指向对象实例本身
- 可以赋值属性,也可以读取属性
- 可以调用类内部的其他方法
- 类内部的所有普通方法第一个参数必须是 self,不写会报错
2.2 示例
class Student:
def study(self, name):
self.name = name # 赋值属性
print(f"{self.name}在学习")
self.sleep() # 调用其他方法
def sleep(self):
print(f"{self.name}在睡觉")
self.make_voice()
def make_voice(self):
print(f"{self.name}打呼噜")
# 创建多个实例,每个实例独立存储数据
s1 = Student()
s2 = Student()
s1.study("张三") # 张三在学习
s2.study("李四") # 李四在学习
3. 对象属性操作
3.1 类内部操作属性
class Teacher:
def teach(self, name='rucy', age=18):
# 通过 self 给属性赋值
self.name = name
self.age = age
print(f"{self.name},{self.age}岁,正在教学")
t = Teacher()
t.teach(name="rucy", age=18)
print(t.name) # 类外部通过实例.属性取值
3.2 类外部操作属性
t = Teacher()
t.name = "张三" # 赋值
t.age = 20
print(t.name) # 取值
3.3 汽车轮子案例
class Car:
def show(self, left_front, right_front, left_back, right_back):
self.left_front = left_front
self.right_front = right_front
self.left_back = left_back
self.right_back = right_back
my_car = Car()
my_car.show("red", "blue", "green", "yellow")
print(my_car.left_front, my_car.right_front) # red blue
# 修改属性
my_car.left_front = "green"
my_car.right_front = "green"
4. 魔法方法
4.1 __init__ — 构造方法
__init__ 在实例对象创建后自动执行,用于初始化属性。相当于构造函数。
class Person:
def __init__(self, name, age, sex, hobby):
self.name = name
self.age = age
self.sex = sex
self.hobby = hobby
print("对象创建完成")
def travel(self):
print(f"{self.name}正在旅行")
p = Person("rucy", 18, "男", "python")
p.travel()
注意:__new__ 在 __init__ 之前执行,但此时还没有 self 实例对象,所以不在 __new__ 中赋值属性。
4.2 __str__ — 字符串化方法
当类被转换成字符串时(如 print(对象))自动执行。必须有返回值,且返回值必须是字符串。
class Person:
def __init__(self, name, age):
self.name = name
self.age = age
def __str__(self):
return f"姓名: {self.name}, 年龄: {self.age}"
p = Person("rucy", 18)
print(p) # 姓名: rucy, 年龄: 18
序列化 = 对象 → 字符串,反序列化 = 字符串 → 对象
4.3 __del__ — 析构方法
当对象被销毁时自动执行,用于释放资源。
class Person:
def __del__(self):
print("对象被销毁了")
p = Person()
del p # 手动销毁,触发 __del__
4.4 其他魔法方法
class Person:
def __add__(self, other):
print("尝试进行加操作")
p = Person()
p + 1 # 触发 __add__
5. 封装
5.1 什么是封装
将数据和方法包装在类内部,对外暴露必要的接口。
5.2 封装示例
class GetMoney:
def get_money(self):
self.go_bank()
self.in_room()
self.insert_card()
# … 封装了取钱的全流程
def go_bank(self):
print("去银行")
def in_room(self):
print("进取款室")
高内聚、低耦合:类和类之间除了必要的依赖外,没有其他融合度。
经验法则:一个函数的代码超过 20 行,就应该拆分。
5.3 私有属性和方法
使用双下划线 __ 开头的属性或方法,只能在类内部访问,不可被继承。
class Utils:
def __reverse_str(self, val=""): # 私有方法
return val[::–1]
def reverse(self, val=""): # 公有方法(桥接)
return self.__reverse_str(val)
u = Utils()
print(u.reverse("abc")) # 输出: cba
# print(u.__reverse_str("abc")) # 报错,外部不能调用私有方法
类外部想要调用类内部的私有方法,通过暴露一个公有方法来桥接。
6. 快速记忆表(上篇)
| 类 | class | 抽象模板 |
| 对象 | 类名() | 模板的具体实现 |
| self | 实例自身 | 类内方法第一个参数 |
| __init__ | 构造方法 | 初始化属性 |
| __str__ | 字符串化 | print() 时触发 |
| __del__ | 析构方法 | 对象销毁时触发 |
| 封装 | 高内聚、低耦合 | 数据+方法打包 |
| 私有 | __属性/方法 | 双下划线开头,类内访问 |




