Python基础教程(第3版)中文版 第16章 测试基础(笔记)

                                          第16章 测试基础


1.先测试再编码


为程序的各个部分编写测试很重要(单元测试)。
“测试一点点,编写一点点”。
1.准确的需求说明
有爱阐述程序的目标,可编写需求说明。
2.做好应对变化的准备

3.测试四步曲
1.确定要实现的功能,记录下来,为之编写测试
2.编写实现功能的框架代码,让程序能够运行,但测试仍无法通过,确保代码不正确时,测试能够报错。
3.编写让测试能通过的代码,无需实现全部,只要能通过测试即可。
4.改进(重构)代码以全面而准确地实现所需的功能,同时确保测试能通过。


2.测试工具


有2个模块可帮助自动完成测试过程。
unittest:通用的测试框架
doctest:为检查文档设计的,也可用来单元测试

1.doctest
实例:
def square(x):
    '''
    计算平方并返回结果
    >>> square(2)
    4
    >>> square(3)
    9
    '''
    return x ** x

if __name__ == '__main__':
    import doctest, my_math
    doctest.testmod(my_math)
保存为my_math.py
然后在命令行运行 python my_math.py
什么都不会输出。
使用 python my_math.py -v 
输出详细信息

2.unittest
实例:
#使用unittest测试 my_math
import unittest, my_math

class ProductTestCase(unittest.TestCase):

    def test_integers(self):
        for x in range(-10, 10):
            for y in range(-10, 10):
                p = my_math.product(x, y)
                self.assertEqual(p, x * y, 'Integer multiplication failed')

    def test_float(self):
        for x in range(-10, 10):
            for y in range(-10, 10):
                x = x / 10
                y = y / 10
                p = my_math.product(x, y)
                self.assertEqual(p, x * y, 'Float multiplication failed')

if __name__ == '__main__': unittest.main()

#被测试的my_math 模块
def product(x, y):
    #这句是故意出错来看看测试是不是有用
    if x == 7 and y == 9:
        return 'An insidious bug has surfaced!'
    return x * y 

3. 超越单元测试


1.使用PyChecker和PyLint检查源代码
PyChecker是检查python源代码的工具,
PyLint支持PyChecker的大部分功能,还有其他功能,如变量名是否规范。。。

由于PyChecker有很多年没有更新了,所以就使用PyLint
直接使用 pip install pylint 安装

使用PyLint 检查文件时,将模块(或包)名作为参数:
pylint module

实例:
#使用模块subprocess调用外部检查器
import unittest, my_math
from subprocess import Popen, PIPE

class ProductTestCase(unittest.TestCase):
    #测试.
    def test_integers(self):
        for x in range(-10, 10):
            for y in range(-10, 10):
                p = my_math.product(x, y)
                self.assertEqual(p, x * y, 'Integer multiplication failed')

    def test_float(self):
        for x in range(-10, 10):
            for y in range(-10, 10):
                x = x / 10
                y = y / 10
                p = my_math.product(x, y)
                self.assertEqual(p, x * y, 'Float multiplication failed')
    
    def test_with_PyLint(self):
        cmd = 'pylint', '-rn', 'my_math'
        pylint = Popen(cmd,stdout=PIPE, stderr=PIPE)
        self.assertEqual(pylint.stdout.read(), '')

if __name__ == '__main__': unittest.main()
#不知道为什么用不了这个方法,所以就直接在命令行用pylint module 了


2.性能分析
通常不需要过分追求速度。但是速度很慢时,就必须优化。性能分析帮助找到运行慢的地方。
标准库模块profile(C语言版本cProfile)
使用时只需调用其方法run并提供一个字符串参数。
>>> import cProfile
>>> from my_math import product
>>> cProfile.run('product(1, 2)')
将输出函数调用次数和花费时间
如果向run提供第二个参数('my_math.profile')将分析结果保存到这个文件中,然后就可以使用模块psats分析结果

猜你喜欢

转载自blog.csdn.net/qq_41068877/article/details/82216653