python怎么测试函数_快学Python:如何测试函数与类

编写代码离不开写测试,只有通过测试才知道代码的逻辑有没有问题,健壮性好不好等,测试让你深信,即便有越来越多的人使用你的程序,它也能一如既往正确地工作。

watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3dlaXhpbl8zMDQ4NDE0OQ==,size_16,color_FFFFFF,t_70#pic_center

1.测试函数

Python标准库中的模块unittest提供了代码测试工具。要进行相关测试,一定要要有待测试的函数,创建文件name_function.py,其内容如下:

def get_formatted_name(first,last,middle = ''):"""生成整洁的姓名"""if middle:full_name = f"{first} {middle} {last}"else:full_name = f"{first} {last}"return full_name.title()

1.1单元测试和测试用例

1)单元测试

用于核实某个函数的某个方面没有问题。

2)测试用例

是一组单元测试,它们一起核实函数在各种情况下的行为都符合要求。

3)全覆盖测试

测试用例包含一整套单元测试,涵盖了各种可能函数使用的方式。

1.2可通过的测试

import unittestfrom name_function import get_formatted_nameclass NamesTestCase(unittest.TestCase):"""Test the name_function.py"""def test_first_last_name(self):"""能够正确处理姓名吗?"""formatted_name = get_formatted_name('sun','wukong')self.assertEqual(formatted_name,'Sun Wukong')if __name__ == '__main__':unittest.main()

运行上面测试用例,运行结果:

.----------------------------------------------------------------------Ran 1 test in 0.000sOK

1.3未通过的测试

为通过测试很容易,将待测试的函数稍微修改下:

def get_formatted_name(first,last,middle = ''):"""生成整洁的姓名"""full_name = f"{first} {middle} {last}"return full_name.title()

运行1.2中的测试用例,则会输出为通过的测试返回。笔者不再尝试。

1.4添加新测试

import unittestfrom name_function import get_formatted_nameclass NamesTestCase(unittest.TestCase):"""Test the name_function.py"""def test_first_last_name(self):"""能够正确处理姓名吗?"""formatted_name = get_formatted_name('sun','wukong')self.assertEqual(formatted_name,'Sun Wukong')def test_first_last_middle_name(self):"""测试三个名字"""formatted_name = get_formatted_name('sun','wu','kong')self.assertEqual(formatted_name,'Sun Kong Wu')if __name__ == '__main__':unittest.main()

运行结果:

..----------------------------------------------------------------------Ran 2 tests in 0.000sOK

2.测试类

2.1各种断言方法

Python在unittest.TestCase类中提供了很多断言方法。下面列举几个常用的断言方法。 方法用途assertEqual(a,b)核实a == b

assertNotEqual(a,b)核实a != b

assertTrue(x)核实x为True

assertFalse(x)核实x为False

assertIn(item,list)核实item在list中

assertNotIn(item,list)核实item不在list中

2.2一个要测试的类

类的测试与函数的测试相似,类的测试基本上都是对方法的测试,不过也存在一些不同之处,下面创建一个匿名调查类来进行测试。

class AnonymousServey:"""收集匿名调查问卷的答案"""def __init__(self,question):"""存储一个问题,并为存储答案做好准备"""self.question = questionself.responses = []def show_question(self):"""显示调查问卷"""print(self.question)def store_response(self,new_response):"""存储单份问卷调查"""self.responses.append(new_response)def show_result(self):"""显示收集到的所有答案"""print("Survey results:")for response in self.responses:print(f"- {response}")

下面编写一个测试,对AnonymousServey类的行为一个方面进行验证:核实答案列表中是否有指定答案。

import unittestfrom survey import AnonymousServeyclass TestAnonymousServey(unittest.TestCase):"""针对AnonymousServey进行测试"""def test_store_single_response(self):question = "What language did you first learn to speak?"self.my_survey = AnonymousServey(question)self.my_survey.store_response('python')self.assertIn('python',self.my_survey.responses)if __name__ == '__main__':unittest.main()

上面的测试类先导入unittest和要测试的AnonymousServey,测试调查问卷的被存储后,测试指定数据是否包含在存储的列表中。我们还可以添加更多维度的测试case,例如测试指定某列表是否包含在存储的列表中。

2.3方法setUp()

如果继续添加测试方法,会有很多重复,如何让公共的变量或者测试数据,在用例执行前就能声明好,而且其他方法都可以公用,如何解决呢?可以使用setUp()函数。结合上面的测试用例,看看如何使用setUp()函数

import unittestfrom survey import AnonymousServeyclass TestAnonymousServey(unittest.TestCase):"""针对AnonymousServey进行测试"""def setUp(self):"""创建一个调查对象和一组答案,供测试方法使用"""question = "What language did you first learn to speak?"self.my_survey = AnonymousServey(question)self.tree_responses = ['java','php','python']def test_store_single_response(self):self.my_survey.store_response(self.tree_responses[0])self.assertIn(self.tree_responses[0],self.my_survey.responses)def test_store_tree_response(self):for response in self.tree_responses:self.my_survey.store_response(response)for response in self.tree_responses:self.assertIn(response,self.my_survey.responses)if __name__ == '__main__':unittest.main()

方法setUp()做了两件事:创建一个调查对象,以及创建一个答案列表。存储这两样东西的变量名包含前缀self(即存储在属性中),因此可以类的任何地方进行使用。

注意:单元测试对于一个程序的健壮形特别重要。但是要想要自己的单元测试覆盖自己所写的每个方法,每一行却不是很容易,需要各种条件的设置,对于第三方的调用还可以使用Mock方式进行,此是后话了。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值