当前位置:首页>python>Python:一文搞懂with与上下文管理器

Python:一文搞懂with与上下文管理器

  • 2026-10-11 07:15:37
Python:一文搞懂with与上下文管理器

在日常开发中,文件操作几乎是最常见的任务之一。但很多初学者在读写文件时,常常忘记关闭文件,导致资源泄露或数据丢失。今天,我们就来聊聊Python文件管理的核心技巧——with语句和上下文管理器,让你写出更优雅、更安全的代码。

文件操作最推荐的写法

with open('a.txt', 'rt', encoding='utf-8') as file:
    for
 line in file:
        print
(line.strip())

这段代码做了三件重要的事:

  • • 自动打开文件(只读文本模式,UTF-8编码)
  • • 逐行读取并打印
  • • 自动关闭文件(即使中途发生异常)
    没错,你不需要手动调用file.close(),with会帮你搞定一切。

with的核心思想:成对操作自动化

Python中的with主要用于管理那些需要成对出现的操作,比如:

  • • 打开 / 关闭
  • • 上锁 / 解锁
  • • 借用一个资源 / 归还一个资源
    最终目标:编码者只管做具体的事情,而“进入”和“离开”的琐事让Python自动处理。
with 上下文管理器表达式 as 变量:
    具体的事情1
    具体的事情2
    ...

上下文管理器协议:揭秘with背后的魔法

任何对象,只要实现了下面两个方法,就可以被with管理:

  • • __enter__(self):with代码块执行之前调用,返回值赋给as后的变量。
  • • __exit__(self, exc_type, exc_val, exc_tb):with代码块执行之后调用(无论是否发生异常)。
    异常参数说明:
  • • exc_type:异常类型
  • • exc_val:异常对象
  • • exc_tb:异常追踪信息
  • • __exit__的返回值决定异常是否继续抛出:
  • • 返回True:异常已被处理,不会再抛出
  • • 返回False:异常未被处理,会继续向上抛出
class Person:
    def
 __init__(self, name, age):
        self
.name = name
        self
.age = age

    def
 __enter__(self):
        print
('我是执行之前的逻辑')
        return
 self   # 返回的对象会赋给 as 后的变量

    def
 __exit__(self, exc_type, exc_val, exc_tb):
        print
('我是执行之后的逻辑')
        # 打印异常信息(如果有的话)

        print
(f'异常类型: {exc_type}')
        print
(f'异常对象: {exc_val}')
        print
(f'异常追踪: {exc_tb}')
        # 返回 False 表示异常仍然向外抛出

        return
 False

    def
 speak(self):
        print
(f'我叫: {self.name}, 今年 {self.age} 岁')

# 使用自定义的上下文管理器

with
 Person('孙悟空', 500) as p1, Person('猪八戒', 800) as p2:
    p1.speak()
    p2.speak()

执行结果

我是执行之前的逻辑
我是执行之前的逻辑
我叫: 孙悟空, 今年 500 岁
我叫: 猪八戒, 今年 800 岁
我是执行之后的逻辑
异常类型: None
异常对象: None
异常追踪: None
我是执行之后的逻辑
异常类型: None
...

open函数的三个核心参数

掌握了with之后,再来看看open函数最常用的三个参数

open(file, mode='r', encoding=None)
参数
说明
file
要操作的文件路径(字符串)
mode
打开模式,由主模式 + 修饰符组成
encoding
字符编码,如utf-8(文本模式下强烈建议指定)

主模式(必选其一)

模式
含义
r
读取(默认)
w
写入,会先清空文件内容
x
排他性创建,如果文件已存在则报错
a
追加写入,文件存在则追加到末尾

修饰符(可选)

修饰符
含义
t
文本模式(默认)
b
二进制模式(如处理图片、视频)
+
更新模式(可读可写)

常用组合示例

  • • rt:以文本方式读取(默认,可省略)
  • • wt:以文本方式写入(会覆盖)
  • • at:以文本方式追加
  • • rb:以二进制方式读取
  • • wb:以二进制方式写入
  • • r+:文本模式读写(不截断文件)

最佳实践总结

  • • 读取文本文件:永远使用with open(..., 'rt', encoding='utf-8') as f:,避免编码问题和资源泄露。
  • • 逐行处理大文件:直接for line in f:,而不是用f.readlines(),后者会把整个文件加载到内存。
  • • 写入文件:使用with open(..., 'wt', encoding='utf-8') as f:,然后f.write()。
  • • 二进制文件:如图片、视频,去掉t并用'rb'或'wb',且不要指定encoding。
  • • 需要手动处理异常? 自定义上下文管理器比try...finally更优雅、可复用。
    希望这篇文章帮你彻底掌握了Python的with和文件操作。以后读写文件,记得闭上眼睛写出:
with open('your_file.txt', 'r', encoding='utf-8') as f:
    for
 line in f:
        # 处理每一行

如果觉得有用,欢迎点赞、在看、转发支持!

最新文章

随机文章