用docstrings测试代码,docstrings是嵌入在Python代码中的字符串,其内容看上去有点像交互式的会话。这些字符串可用来检验某些假设,或者仅仅把它们看作是一些范例代码。我们需要用doctest模块运行这些测试。
让我们写一个简单的程序来计算阶乘,但该程序没有覆盖所有可能的边界条件。也就是说,某些测试项目是通不过的。
具体步骤
- 编写docstring。
编写一个包含两个测试项目的docstring,其中一个测试项目可以通过,另一个通不过。这个docstring看起来像是Python shell中的会话。
"""
Test for the factorial of 3 that should pass.
>>> factorial(3)
6
Test for the factorial of 0 that should fail.
>>> factorial(0)
1
"""
- 编写NumPy代码。
编写如下的NumPy代码。
return numpy.arange(1, n+1).cumprod()[-1]
该行代码将创建一个由顺序加1的数构成的数组,计算其累积连乘,并返回计算结果的最后一个元素。我们有意让上述代码在某些时候出错。
- 执行测试。
前面已经提到,我们需要使用doctest模块执行测试。
doctest.testmod()
求阶乘和用docstring做测试的完整范例代码如下。
import numpy
import doctest
def factorial(n):
"""
Test for the factorial of 3 that should pass.
>>> factorial(3)
6
Test for the factorial of 0 that should fail.
>>> factorial(0)
1
"""
return numpy.arange(1, n+1).cumprod()[-1]
doctest.testmod()
使用-v
选项可以获得详细的输出结果,如下所示。
python docstringtest.py -v
Trying:
factorial(3)
Expecting:
6
ok
Trying:
factorial(0)
Expecting:
1
**********************************************************************
File "docstringtest.py", line 11, in __main__.factorial
Failed example:
factorial(0)
Exception raised:
Traceback (most recent call last):
File ".../doctest.py", line 1253, in __run
compileflags, 1) in test.globs
File "<doctest __main__.factorial[1]>", line 1, in <module>
factorial(0)
File "docstringtest.py", line 14, in factorial
return numpy.arange(1, n+1).cumprod()[-1]
IndexError: index out of bounds
1 items had no tests:
__main__
**********************************************************************
1 items had failures:
1 of 2 in __main__.factorial
2 tests in 2 items.
1 passed and 1 failed.
***Test Failed*** 1 failures.
攻略小结
如你所见,我们没有考虑对0和负数求阶乘的情况。实际上,由于出现了数组为空的情况,我们得到了一个索引超出边界(index out of bounds)错误。当然这个错误很容易修正,我们将在下章完成此事。