Python 文档测试
文档测试(doctest)是Python内置的测试工具,通过在函数、类或模块的文档字符串(docstring)中嵌入测试用例,验证代码行为。它结合了文档和测试,适合快速验证代码的正确性。doctest通过模拟交互式Python会话,检查代码输出是否与预期一致。
编写第一个doctest
文档测试通常写在函数的文档字符串中,格式为>>>
后跟代码,下一行是预期输出。以下是一个简单示例:
def add(a, b):
"""加法函数。
>>> add(2, 3)
5
>>> add(-1, 1)
0
"""
return a + b
if __name__ == "__main__":
import doctest
doctest.testmod()
运行此代码时,doctest.testmod()
会扫描文档字符串中的测试用例,执行并验证输出。无错误时无输出,有错误则显示失败详情。
doctest的语法规则
- 测试用例以
>>>
开头,模拟Python交互式环境。 - 预期输出紧跟在
>>>
代码的下一行,无需额外符号。 - 多行输出需精确匹配,包括换行和空格。
- 异常测试使用
>>>
后跟Traceback
描述,例如:
def divide(a, b):
"""除法函数。
>>> divide(6, 2)
3.0
>>> divide(5, 0)
Traceback (most recent call last):
...
ZeroDivisionError: division by zero
"""
return a / b
if __name__ == "__main__":
import doctest
doctest.testmod()
测试复杂输出
对于复杂数据结构(如列表或字典),确保输出格式一致。可以使用doctest
的选项标志(如+ELLIPSIS
)简化匹配:
def get_list():
"""返回一个列表。
>>> get_list() # doctest: +ELLIPSIS
[...]
"""
return [1, 2, 3]
if __name__ == "__main__":
import doctest
doctest.testmod()
+ELLIPSIS
允许用...
匹配任意内容,适合不可预测的输出部分。
在模块级别编写doctest
模块级别的doctest写在模块顶部的文档字符串中,适合测试全局函数或模块行为:
"""
这是一个计算平方和的模块。
>>> square_sum(3, 4)
25
"""
def square_sum(a, b):
return a**2 + b**2
if __name__ == "__main__":
import doctest
doctest.testmod()
使用doctest运行测试
有三种方式运行doctest:
- 代码内运行:如上,使用
doctest.testmod()
。 - 命令行运行:保存代码为
example.py
,运行python -m doctest example.py -v
(-v
显示详细输出)。 - 集成到unittest:将doctest嵌入unittest框架:
import doctest
import unittest
def multiply(a, b):
"""乘法函数。
>>> multiply(2, 3)
6
>>> multiply(0, 5)
0
"""
return a * b
def load_tests(loader, tests, ignore):
tests.addTests(doctest.DocTestSuite())
return tests
if __name__ == "__main__":
unittest.main()
doctest的优缺点
优点:
- 测试与文档结合,易于维护。
- 简单易用,适合快速验证。
- 内置模块,无需额外安装。
缺点:
- 不适合复杂测试场景(如依赖外部资源)。
- 输出格式需严格匹配,维护成本可能较高。
- 难以测试非确定性输出。