Python异常捕获:让代码更稳的实用技巧

Python代码时,谁还没遇到过程序突然报错崩溃的情况?比如读文件时发现文件不存在,或者网络请求超时。这些问题如果不管,用户点一下就闪退,体验极差。其实用好异常捕获,就能让程序在出问题时不慌,还能给出提示或自动处理。

try-except 最基础也最常用

最常见的写法就是用 try 包住可能出错的代码,用 except 捕获异常。比如你写了个小脚本要读配置文件,但用户删了这个文件:

try:
    with open('config.txt', 'r') as f:
        data = f.read()
except FileNotFoundError:
    print('配置文件没找到,使用默认设置')
    data = 'default_config'

这样程序不会直接崩,而是继续运行,用户体验就好多了。

捕获多种异常情况

有时候一段代码可能出多种错。比如网络请求,可能连接失败,也可能超时。可以写多个 except 分别处理:

import requests

def get_user_info(url):
    try:
        response = requests.get(url, timeout=5)
        return response.json()
    except requests.exceptions.Timeout:
        print('请求超时,换个时间再试')
    except requests.exceptions.ConnectionError:
        print('网络连接失败,请检查网络')
    except ValueError:
        print('返回的数据不是合法JSON')

不同问题给不同反馈,排查起来也方便。

finally 用来收尾

有些操作不管成功失败都得执行,比如关闭文件、释放资源。这时 finally 就派上用场了:

file_handle = None
try:
    file_handle = open('log.txt', 'w')
    file_handle.write('开始记录')
    result = 10 / 0  
except Exception as e:
    print(f'出错了:{e}')
finally:
    if file_handle:
        file_handle.close()
        print('文件已关闭')

哪怕中间出错跳到 except,finally 里的关闭操作依然会执行,避免资源泄露。

主动抛出异常用 raise

不只是系统会报错,你自己也能在条件不满足时主动抛异常。比如函数要求传正数,结果传了个负的:

def set_age(age):
    if age < 0:
        raise ValueError('年龄不能是负数')
    print(f'设置年龄为 {age}')

调用时就可以用 try 去接这个错误,统一处理。

用 as 获取具体错误信息

很多时候只知道出了错还不够,还得知道错在哪。except 后面加 as 可以拿到异常实例:

try:
    num = int(input('输入一个数字:'))
except ValueError as e:
    print(f'输入格式不对,错误详情:{e}')

打印出来的 e 通常会包含具体原因,比如“invalid literal for int()”,调试时特别有用。

异常捕获不是为了掩盖问题,而是让程序更健壮。日常写脚本、做自动化、甚至爬虫,加上合适的 try-except,能少掉很多头发。