目录

一、封装:数据安全与逻辑隐藏的 “保护壳”

1. 封装的两层核心含义

2. 私有成员:如何定义与访问限制

3. 私有成员的 “安全接口”:get_xx 与 set_xx

4. 封装的实际意义

二、继承:代码重用与类的 “层级关系”

1. 继承的基本概念与语法

2. 继承的关键特性

2.1 单继承与多层继承的 “传递性”

2.2 多继承:灵活但需谨慎

 2.3 MRO:方法解析顺序

2.4 super ():调用父类成员

3. 方法重写:子类的 “个性化改造”

三、多态:灵活调用与 “接口统一”

1. 多态的实现条件

2. 多态的代码实现

3. Python 中的内置多态案例

4. 多态的价值


在 Python 面向对象编程(OOP)中,类与对象是基础,但当面对复杂项目时,仅靠基础语法远远不够。进阶的面向对象特性 ——封装、继承、多态,以及类属性、类方法等扩展特性,是实现代码模块化、可维护性与可扩展性的核心。本文将结合实战案例,系统梳理这些进阶操作,帮你真正掌握面向对象的设计思想。

一、封装:数据安全与逻辑隐藏的 “保护壳”

封装是面向对象的基石,核心思想是 “隐藏内部细节,暴露安全接口”。它不仅能保护数据不被随意修改,还能降低代码的复杂度。

1. 封装的两层核心含义

根据文档内容,Python 中的封装包含两个关键维度:

(1)维度 1:属性与方法的 “聚拢”
将现实世界中 “实体” 的属性(特征)和方法(行为)封装到同一个类中,形成一个独立的 “代码单元”。例如 “员工” 的姓名、年龄(属性)和打卡、领工资(方法),都定义在Workers类中,符合现实逻辑。

(2)维度 2:私有权限的 “隔离”
对敏感属性或方法设置 “私有权限”,禁止外部直接访问,仅通过预设的 “接口” 操作 —— 这是封装的核心价值。

2. 私有成员:如何定义与访问限制

Python 中通过属性 / 方法名前加两个下划线(__) 定义私有成员,其本质是 “名称修饰”,防止外部直接篡改。

示例:私有属性的定义与访问限制

class Girl():
    def __init__(self, name):
        self.name = name  # 公有属性:外部可直接访问
        self.__age = 18   # 私有属性:外部禁止直接访问

# 测试
xiaomei = Girl("小美")
print(xiaomei.name)  # 正常输出:小美
print(xiaomei.__age) # 报错!提示无__age属性(私有成员被隐藏)

3. 私有成员的 “安全接口”:get_xx 与 set_xx

若需访问私有成员,需在类内部定义公共接口(方法),通常命名为get_xx(获取)和set_xx(修改)。接口中还可添加逻辑验证,过滤异常数据。

示例:为私有属性添加访问接口

class Girl():
    def __init__(self, name):
        self.name = name
        self.__age = 18  # 私有属性

    # 接口1:获取私有属性
    def get_age(self):
        return self.__age

    # 接口2:修改私有属性(带验证)
    def set_age(self, age):
        if 0 < age < 120:  # 过滤无效年龄
            self.__age = age
        else:
            print("年龄无效!")

# 测试
xiaomei = Girl("小美")
xiaomei.set_age(19)    # 合法修改
print(xiaomei.get_age())# 输出:19
xiaomei.set_age(200)   # 输出:年龄无效!

4. 封装的实际意义

(1)数据保护:避免外部随意修改敏感数据(如银行账户余额)。
案例:BankAccount类将余额__balance设为私有,仅通过deposit()(存款)和withdraw()(取款)接口操作,防止余额被篡改。

(2)降低复杂度:隐藏内部实现细节,外部只需调用接口。
案例:ATM类将 “插卡(__card)、认证(__auth)” 等私有方法隐藏,对外仅暴露withdraw()(取款)一个接口,用户无需关心内部流程。

二、继承:代码重用与类的 “层级关系”

继承是实现代码重用的核心手段,它允许子类(派生类)复用父类(基类)的公共属性和方法,同时添加自身的个性化特性。

1. 继承的基本概念与语法

(1)核心逻辑:体现 “共性与个性” 的关系(如 “动物→狗”“汽车→电动车”)。

(2)基本语法class 子类名(父类名):(Python3 中父类默认继承object,建议显式声明)。

示例:单继承的代码重用

# 父类:汽车(共性)
class Car(object):
    def __init__(self, brand, color):
        self.brand = brand  # 品牌(共性属性)
        self.color = color  # 颜色(共性属性)
    
    def run(self):
        print(f"{self.brand}在行驶")  # 共性方法

# 子类:电动车(个性)
class ElectricCar(Car):
    # 新增个性属性:电池容量
    def __init__(self, brand, color, battery):
        # 调用父类构造方法,复用共性属性初始化
        super().__init__(brand, color)
        self.battery = battery  # 个性属性

    # 重写父类方法,实现个性行为
    def run(self):
        print(f"{self.brand}电动车(电池{self.battery}kwh)静音行驶")

# 测试
tesla = ElectricCar("特斯拉", "红色", 70)
tesla.run()  # 输出:特斯拉电动车(电池70kwh)静音行驶

2. 继承的关键特性

2.1 单继承与多层继承的 “传递性”

(1)单继承:一个子类仅继承一个父类(Python 推荐方式,避免复杂度)。

(2)多层继承:子类继承父类,父类再继承祖父类,子类会自动继承所有上层类的公共成员(传递性)。

# 祖父类:生物
class Creature(object):
    def breathe(self):
        print("呼吸空气")

# 父类:动物(继承生物)
class Animal(Creature):
    def eat(self):
        print("吃食物")

# 子类:狗(继承动物)
class Dog(Animal):
    def bark(self):
        print("汪汪叫")

# 测试:Dog继承了Creature和Animal的方法
wangcai = Dog()
wangcai.breathe()  # 输出:呼吸空气(来自Creature)
wangcai.eat()      # 输出:吃食物(来自Animal)
wangcai.bark()     # 输出:汪汪叫(来自自身)

2.2 多继承:灵活但需谨慎

Python 支持多继承(一个子类继承多个父类),但易产生 “方法冲突”(多个父类有同名方法),需通过MRO(方法解析顺序) 解决。

# 父类1:汽油车
class GasolineCar(object):
    def run(self):
        print("烧汽油行驶")

# 父类2:电动车
class ElectricCar(object):
    def run(self):
        print("用电行驶")

# 子类:混合动力车(多继承)
class HybridCar(GasolineCar, ElectricCar):
    pass

# 测试:方法冲突时,按继承顺序(先GasolineCar)调用
hybrid = HybridCar()
hybrid.run()  # 输出:烧汽油行驶

 2.3 MRO:方法解析顺序

当多继承出现方法冲突时,Python 按MRO 规则查找方法:

(1)先在子类自身查找;

(2)再按父类继承顺序(如HybridCar(GasolineCar, ElectricCar))查找;

(3)最后追溯到object类。

通过类名.__mro__或类名.mro()查看 MRO:

print(HybridCar.__mro__)
# 输出:(HybridCar, GasolineCar, ElectricCar, object)

2.4 super ():调用父类成员

super()用于在子类中调用父类的属性或方法,避免硬编码父类名,尤其适合多层继承。

(1)语法:Python3 中简化为super().方法名()(无需传self或父类名)。

3. 方法重写:子类的 “个性化改造”

子类可重写父类的方法(同名方法),实现个性化行为 —— 这是多态的基础。重写后,子类实例优先调用自身方法,父类方法仍存在但需通过super()调用。

# 父类:动物
class Animal(object):
    def call(self):
        print("动物发出叫声")

# 子类1:狗(重写call方法)
class Dog(Animal):
    def call(self):
        print("汪汪叫")

# 子类2:猫(重写call方法)
class Cat(Animal):
    def call(self):
        print("喵喵叫")

# 测试
wangcai = Dog()
wangcai.call()  # 输出:汪汪叫(子类方法)
miaomiao = Cat()
miaomiao.call() # 输出:喵喵叫(子类方法)

三、多态:灵活调用与 “接口统一”

多态是面向对象的 “高级能力”,核心思想是 “同一接口,不同实现”—— 调用相同的方法,不同对象返回不同结果,无需关心对象具体类型。

1. 多态的实现条件

要实现多态,需满足两个前提:

  1. 继承关系:子类继承父类(非绝对,但 Python 中多基于继承实现);
  2. 方法重写:子类重写父类的公共方法(接口)。

2. 多态的代码实现

通过 “公共接口函数” 调用不同子类对象的方法,体现多态特性。

示例:水果榨汁的多态实现

# 父类:水果(定义公共接口)
class Fruit(object):
    def make_juice(self):
        print("制作果汁")

# 子类1:苹果(重写接口)
class Apple(Fruit):
    def make_juice(self):
        print("制作苹果汁")

# 子类2:香蕉(重写接口)
class Banana(Fruit):
    def make_juice(self):
        print("制作香蕉汁")

# 公共接口函数(统一调用方式)
def juice_service(fruit):
    fruit.make_juice()  # 调用相同方法,不同对象有不同行为

# 测试:多态体现
juice_service(Apple())  # 输出:制作苹果汁
juice_service(Banana()) # 输出:制作香蕉汁

3. Python 中的内置多态案例

Python 原生支持多态,最典型的是运算符+

(1)两个数字相加:1 + 2 = 3(算术运算);

(2)两个字符串拼接:"a" + "b" = "ab"(字符串合并);

(3)两个列表合并:[1,2] + [3,4] = [1,2,3,4](序列合并)。

本质是不同类型的对象,重写了+对应的__add__方法,体现 “同一接口(+),不同实现”。

4. 多态的价值

(1)代码通用化:接口函数(如juice_service)无需修改,即可适配新的子类(如新增 “橘子” 类);

(2)降低耦合度:调用者无需关心对象具体类型,只需关注接口是否一致,便于扩展。

Logo

Agent 垂直技术社区,欢迎活跃、内容共建。

更多推荐