课程库 › AI 主线 › 文件与自动化脚本 › 第 1 课
读写文本文件 —— 数据的持久化
普通课约 55 分钟
本课导读
到目前为止,你程序里的数据都有个致命弱点:程序一结束,全部失忆——变量、列表、对象,统统蒸发。本课学会把数据写进文件、再从文件读回来(术语叫"持久化"),你的程序从此有了记忆。这也是本单元"干活功夫"的第一块地基:后面的 CSV、JSON、批量整理,全建在它上面。预计 55 分钟。
说明
练习场说明:本单元的代码在浏览器里的虚拟磁盘上操作文件——它是 Python 运行环境自带的沙盒空间,放心折腾,碰不到你电脑上的真实文件;刷新页面就清空,所以每个代码块都会自己先造好需要的文件。等 U1.4 装好本地环境,同样的代码就能操作真实文件——功夫是通用的。
写文件:三行代码的仪式
运营小林想把每天的复盘记下来。写文件的标准姿势:
逐个零件拆:
open("diary.txt", "w", ...)——打开(不存在就创建)文件。"w"是写模式(write):⚠️ 同名文件会被整个清空重写encoding="utf-8"——指定编码。写中文必带,跨系统不乱码的保命参数,从第一天就养成习惯as f——给打开的文件起个代号 f,之后f.write(...)往里写;\n手动换行(write 不像 print 会自动换)with ...:——自动关门器。文件用完必须关闭(否则数据可能没真正落盘);with 块一结束自动帮你关,忘不了
提示
类比记忆:操作文件像去银行办事——open 是取号进门,读写是办业务,关闭是离开柜台。with 语句 = 自动感应门:业务办完(缩进块结束)门自动关,永远不会忘。裸写 f = open(...) 再手动 f.close() 也行,但何必拒绝自动门呢——本课程一律用 with。
读文件:三种姿势
- 读模式
"r"是默认值,可以不写;读不存在的文件会报FileNotFoundError(异常课的知识马上要用了) - 三种姿势选择:要整块文本用
read();要按行处理用for line in f(逐行喂,不一次吞下,文件再大也稳) line.strip()是读文件的标配——每行末尾都拖着换行符,不洗掉后患无穷
追加模式:"a" 不清空,接着写
日记这种场景,每天写一条,"w" 模式会把昨天的清掉——换追加模式 "a"(append):
三种模式排排站:
| 模式 | 名字 | 行为 | 典型场景 |
|---|---|---|---|
"r" | 读 | 只读,不存在报错 | 读配置、读数据 |
"w" | 写 | 清空重写,不存在则创建 | 导出结果、生成报告 |
"a" | 追加 | 末尾接着写,不存在则创建 | 日志、日记、流水账 |
说明
本课最贵的坑:"w" 会不声不响清空旧文件。对着辛苦攒了半年的数据文件手滑写了个 "w",比任何报错都惨——报错还能改,清空没得哭。写代码前默念:导出用 w,积累用 a。
组合拳:读进来 → 加工 → 写回去
文件功夫和之前所有功夫是一套连招。行政小美有一份报名名单,要清洗后另存(还记得 U1.1 的清洗流水线吗):
新面孔 enumerate(names, 1):遍历列表时同时拿到序号和元素(从 1 起数),比手动维护计数器体面——文件处理里出场率极高,混个脸熟。
这套"读 → 加工 → 写"三段式,就是一切自动化脚本的骨架。后面几课只是把"加工"换成 CSV 解析、JSON 解析、批量改名而已。
✍️ 练习
练习 1:购物清单存取
把列表里的三样东西写进 shopping.txt(每样一行),再读出来逐行打印成"☐ 物品名"的待办样式。
✅ 参考答案
items = ["键盘", "降噪耳机", "显示器支架"]
with open("shopping.txt", "w", encoding="utf-8") as f:
for item in items:
f.write(item + "\n")
with open("shopping.txt", encoding="utf-8") as f:
for line in f:
print(f"☐ {line.strip()}")
练习 2:积分流水账
写函数 log_points(name, points):往 points.log 追加一行 姓名,分数。调用三次(其中同一人两次),再读出整个文件确认三条都在。
💡 提示
积累型场景用 "a" 模式——用 "w" 的话第三次调用后文件里只剩一行。
✅ 参考答案
def log_points(name, points):
with open("points.log", "a", encoding="utf-8") as f:
f.write(f"{name},{points}\n")
log_points("小雨", 20)
log_points("阿杰", 15)
log_points("小雨", 30)
with open("points.log", encoding="utf-8") as f:
print(f.read())
顺便埋个钩子:这种"逗号分隔"的行,其实就是最朴素的 CSV——下一课正式认识它。
练习 3:健壮的读取(挑战)
写函数 read_or_empty(filename):文件存在就返回行列表(洗净换行),不存在不崩溃,返回空列表。分别用存在和不存在的文件各测一次。(U1.1 异常课的气囊该上场了。)
💡 提示
读不存在的文件报 FileNotFoundError——把 with open 那段放进 try,except 它返回 []。
✅ 参考答案
def read_or_empty(filename):
try:
with open(filename, encoding="utf-8") as f:
return [line.strip() for line in f]
except FileNotFoundError:
return []
with open("exists.txt", "w", encoding="utf-8") as f:
f.write("有货\n")
print(read_or_empty("exists.txt"))
print(read_or_empty("ghost.txt")) # 不崩,安静地返回 []
"文件读取"正是异常课说的"检查了也可能出意外"的主场——预防(先判断存在)和气囊(except)在这里都常见,气囊更省事。
📝 随堂测验
1. 用 "w" 模式打开一个已有内容的文件,会发生什么?
2. with open(...) as f: 里 with 的作用是?
3. open 时写 encoding="utf-8" 是为了?
4. for line in f: 逐行读时,line 末尾通常拖着什么?
5. 读取一个不存在的文件会报什么错?
本课小结
- 持久化 = 把数据写进文件,程序结束也不失忆;骨架是"读 → 加工 → 写"三段式
- 标准姿势:
with open(路径, 模式, encoding="utf-8") as f:——with 自动关门,utf-8 保命 - 三模式:r 读(默认)/ w 清空重写 / a 追加;读不存在的文件报 FileNotFoundError
- 逐行读用
for line in f+line.strip()标配;enumerate遍历顺便发号
下一课认识职场文件一号选手:CSV——Excel 的素颜形态,用标准库把表格数据读进 Python。
划选正文任意文字可高亮、批注或加入复习卡
讨论
载入中…