教程建议 35 分钟学习等级 4/8

PYTHON LESSON 055

电子宠物养成记

认识类与对象,会用 __init__ 创建带属性的对象,会定义和调用方法。

00 · 学习目标

这一课要解决什么?

先想一想游戏里每只宠物都有自己的饥饿值,代码怎样装下“很多只”?
完成任务会吃会玩的电子宠物
学习顺序定义 → 语法 → 最小实例 → 独立练习

学完后,你应该能够

  • class 类名: 画出一张图纸
  • __init__ 创建对象时自动执行
  • 对象.方法() 让对象自己做事

01 · 核心概念

类的创建:__init__、属性与方法

类的创建:__init__、属性与方法:类(class)是一张图纸,规定“宠物”都有什么属性、会做什么事;对象是按图纸造出来的具体产品。一张图纸可以造出千千万万只宠物,每只都有自己的数值。

考级对应GESP Python 4 级 · 类的创建
学习边界

课程使用普通类解释对象模型;dataclass、property、抽象基类和元类是后续工程工具。

02 · 语法与规则

先记住这 3 条,再开始写程序

01class 类名: 画出一张图纸

先准确读出这条写法的结构与作用。

02__init__ 创建对象时自动执行

换一组最小数据,手工推演一次结果。

03对象.方法() 让对象自己做事

再用边界值或反例确认它的适用条件。

03 · 完整实例

代码、运行结果和解释放在一起看

virtual-pet.pyPYTHON 3.12
# 电子宠物养成记:类的创建
class Pet:
    """一只电子宠物:有名字、种类、饥饿值和心情值"""
    def __init__(self, name, kind):
        self.name = name      # 属性:名字
        self.kind = kind      # 属性:种类
        self.hunger = 50      # 属性:饥饿值(越大越饿)
        self.mood = 50        # 属性:心情值

    def feed(self):
        """喂食:饥饿值下降"""
        self.hunger = self.hunger - 20
        print(f"{self.name}吃饱了,饥饿值降到 {self.hunger}")

    def play(self):
        """玩耍:心情值上升,饥饿值上升"""
        self.mood = self.mood + 15
        self.hunger = self.hunger + 10
        print(f"{self.name}玩得很开心,心情 {self.mood},饥饿 {self.hunger}")

    def status(self):
        """汇报当前状态"""
        print(f"[{self.kind}]{self.name}:饥饿 {self.hunger},心情 {self.mood}")

# 按图纸(类)造出两只宠物(对象)
cat = Pet("咪咪", "小猫")
dog = Pet("旺财", "小狗")

cat.feed()
cat.play()
dog.play()
cat.status()
dog.status()
运行结果OUTPUT
咪咪吃饱了,饥饿值降到 30
咪咪玩得很开心,心情 65,饥饿 40
旺财玩得很开心,心情 65,饥饿 60
[小猫]咪咪:饥饿 40,心情 65
[小狗]旺财:饥饿 60,心情 65

self 指“这只宠物自己”:每个对象的属性各存一份,互不干扰。

在新标签运行和修改这个实例已装入本课代码 · 可自定义输入 · 可提交判题

04 · 逐步理解

每一步只解决一个问题

  1. 01

    类是图纸,对象是产品

    类(class)是一张图纸,规定“宠物”都有什么属性、会做什么事;对象是按图纸造出来的具体产品。一张图纸可以造出千千万万只宠物,每只都有自己的数值。

    PYTHON
    class Pet:
  2. 02

    __init__:出生证明

    Pet("咪咪", "小猫") 一执行,__init__ 自动运行,把名字、种类写在这只宠物的“出生证明”上,并给饥饿值、心情值赋上初始值 50。

    PYTHON
    def __init__(self, name, kind):
        self.name = name
        self.kind = kind
  3. 03

    self 是“我自己”

    每个方法的第一个参数都叫 self,指“这个对象自己”。cat.feed() 执行时,self 就是 cat,改的是 cat 的饥饿值;dog.feed() 时 self 就是 dog。self 让同一份代码服务每一只宠物。

    PYTHON
    self.hunger = self.hunger - 20
  4. 04

    方法就是对象会做的事

    方法和函数长得一样,只是写在类里面、第一个参数是 self。feed、play、status 定义了宠物的本领;用“对象.方法()”的格式让它施展本领。

    PYTHON
    cat.feed()
    cat.status()
  5. 05

    两只宠物,互不干扰

    cat 玩耍后心情 65,dog 玩耍后也是 65——各自从 50 算起。属性存在每个对象自己身上,这正是类最强大的地方:批量管理“同一类东西,各有各的数据”。

  6. 06

    给宠物加技能

    试着给 Pet 加一个新方法 sleep():心情 +10、饥饿 +5。再养一只 Pet("团团", "熊猫"),喂它、陪它玩,最后用 status() 验收你的宠物乐园。

    PYTHON
    def sleep(self):
        self.mood = self.mood + 10

05 · 练习与检验

自己写出来,才算真正学会

本课实作步骤
  1. 1运行程序,养出小猫和小狗
  2. 2再养第三只宠物,互不影响
  3. 3给宠物加一个新方法 sleep
  4. 4连续喂食三次,观察饥饿值变化
打开本课编程实验室编辑、运行、测试、判题都在一个页面完成

06 · 完整知识

继续理解定义、规则和适用边界

第一次学习先完成上面的六个步骤;需要查定义、核对规则、分析误区或理解“为什么”时,再展开对应知识章。

程序组织类、对象、属性与方法理解对象模型和封装边界,用类表达有状态的实体,而不是把所有程序都强行改成类。

正式定义

类描述一类对象的数据与行为;实例是类创建的具体对象。实例方法的第一个参数通常命名为 self,用来访问当前实例;__init__ 在实例创建后负责初始化状态。

必须掌握

  • 实例属性通常在 __init__ 中通过 self.name = value 建立。
  • 实例方法通过 object.method() 调用;Python 会自动把实例绑定给 self。
  • 类属性由实例共享,实例属性属于单个对象;同名实例属性会遮蔽类属性。
  • __repr__ 面向开发与调试,__str__ 面向用户显示;特殊方法应遵守其协议。
  • 继承表达“是一种”关系,组合表达“拥有一个”关系;能用组合清晰表达时不要滥用继承。
  • 对象相等默认仍是身份比较;需要按内容相等时要定义相应协议。

常见误区

  • 在方法中漏写 self
  • 把每个实例独有的可变数据写成类属性
  • 只为包装几个无状态函数而建类
  • 继承层次过深导致行为难以追踪

适用边界

  • 课程使用普通类解释对象模型;dataclass、property、抽象基类和元类是后续工程工具。
  • 算法题常用函数和基本容器更直接,不要求为了“面向对象”而增加结构。
打开本章完整示例与独立阅读页 →
程序组织函数、参数、返回值与作用域用明确的输入、输出和职责拆分程序,理解参数绑定、作用域、递归与可变对象。

正式定义

函数把一段可复用行为绑定到名字。调用时实参按规则绑定到形参,函数执行后用 return 交回结果;没有显式 return 时返回 None。名字解析遵循局部、闭包、全局、内置的 LEGB 顺序。

必须掌握

  • 位置参数先于关键字参数;默认值在 def 执行时创建一次,不应直接使用可变容器作默认值。
  • return 立即结束当前函数;return a, b 实际返回一个元组。
  • 函数内赋值默认创建局部变量;global 声明模块级名字,nonlocal 声明最近外层函数名字。
  • 传参传递的是对象引用;函数是否影响调用方取决于对象是否可变以及函数是否原地修改。
  • 递归必须有可到达的终止条件,并要考虑调用深度、重复子问题和栈空间。
  • 纯函数更容易测试;把输入输出、计算逻辑和全局状态分开能显著减少错误。

常见误区

  • 可变默认参数在多次调用间共享
  • 忘记 return 导致得到 None
  • 局部变量遮蔽全局同名变量
  • 递归没有缩小问题规模

适用边界

  • lambda 只能包含一个表达式,适合短小的排序键,不适合塞入复杂业务逻辑。
  • 装饰器、生成器和闭包属于函数模型的进阶应用,应在基本参数与作用域稳定后学习。
打开本章完整示例与独立阅读页 →
核心数据结构树、图、DFS、BFS 与最短路从节点与边的模型出发,掌握遍历、连通性、树结构、最小生成树和最短路径的适用条件。

正式定义

图由顶点和边构成;树是连通且无环的无向图。DFS 沿路径深入后回溯,BFS 按距离层次扩展。算法的正确选择取决于图是否有向、边权是否为负、是否稠密以及目标是遍历、连通还是最短路。

必须掌握

  • 邻接矩阵占 O(V²) 空间,适合稠密图和快速查边;邻接表占 O(V+E),适合稀疏图。
  • DFS 常用递归或显式栈,BFS 使用队列;一般图都必须记录 visited 防止重复和死循环。
  • 无权图的 BFS 首次到达即得到最少边数距离,可用 parent 还原路径。
  • 树有 V-1 条边且任意两点路径唯一;二叉树前/中/后序描述根的访问时机。
  • Dijkstra 只适用于非负边权;Floyd 求所有点对最短路并允许负边,但不能有可达负环。
  • Kruskal 按边权排序并用并查集避环,得到连通无向带权图的最小生成树。

常见误区

  • 遍历一般图时不记录 visited
  • 对负权边使用 Dijkstra
  • 混淆最短路径树与最小生成树
  • 递归 DFS 忽略深度限制

适用边界

  • 有向无环图、拓扑排序、强连通分量和负权最短路是图论后续主题。
  • 网格搜索也是图搜索:格子是顶点,可移动关系是边;不要只背二维数组模板。
打开本章完整示例与独立阅读页 →
完整速查Python 关键字、内置名称与语法速查集中查阅 Python 3.12 的 35 个硬关键字、4 个软关键字和课程常用内置函数,避免知识碎片化。

正式定义

关键字是 Python 语法保留的词,不能作为普通标识符;软关键字只在特定语法位置有特殊含义。内置名称由 builtins 模块提供,可以直接使用,但仍可能被同名变量遮蔽。

必须掌握

  • Python 3.12 有 35 个硬关键字;False、None、True 首字母大写。
  • match、case、_、type 是软关键字,只在对应模式匹配或类型参数语法环境中特殊。
  • 内置函数无需 import,但不要把变量命名为 list、str、sum、max、input 等。
  • help(name) 查看运行时帮助,dir(object) 查看可用名称,type(object) 查看类型。
  • 内置异常类也是内置名称;捕获异常时应使用具体异常类型。
  • 本站课程运行基线是 Python 3.12,跨版本新增语法必须先核对目标运行环境。

常见误区

  • 把内置名称误称为关键字
  • 用 list = [] 遮蔽 list()
  • 照搬其他 Python 版本的关键字表
  • 见到陌生函数名就假定无需导入

适用边界

  • 本页完整列出语言关键字,并列出课程实际依赖的内置函数;Python 的全部内置异常类和对象协议应按具体错误与主题查阅。
  • 第三方库 API 不属于 Python 语言本身,也不属于内置名称。
打开本章完整示例与独立阅读页 →

完成检查

确认自己会解释、会编写、会验证