Unittest from a dictionary of functions and values
我刚接触过Python中的
1 2 3 4 5 | petersen_prop = { "n_vertex" : 10, "n_edge" : 15, ... } |
每个"键"都是一个函数的名称,值是我希望UnitTests验证的目标。有效的是相当冗长的代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 | import unittest class PetersenGraph(unittest.TestCase): def setUp(self): # Create the graph here (not important to the question) self.args = args self.adj = adj def test_n_vertex(self): self.assertTrue(n_vertex(self.adj,**self.args) == petersen_prop["n_vertex"]) def test_n_edge(self): self.assertTrue(n_edge(self.adj,**self.args) == petersen_prop["n_edge"]) # ..... hundreds of similar looking code blocks unittest.main(verbosity=2) |
似乎我违反了dry,我不得不反复复制和粘贴相同的代码块。是否有一种以编程方式添加这些代码块的方法,以便单元测试能够按预期工作?为了清楚起见,我希望输入是上面的字典,输出是一个工作相同的UnitTest对象。
您可以迭代
1 2 3 4 5 | def test_n_props(self): for cur_prop in petersen_prop: func = globals()[cur_prop] self.assertTrue(func(self.adj,**self.args) == petersen_prop[cur_prop]) |
或者,如果没有将所有函数名导入到测试模块的命名空间中,则如下所示:
1 2 3 4 5 | def test_n_props(self): for cur_prop in petersen_prop: func = getattr(myfuncs, cur_prop) self.assertTrue(func(self.adj,**self.args) == petersen_prop[cur_prop]) |
还可以将实际函数对象存储在
1 2 3 4 5 6 7 8 9 10 11 | petersen_prop = { "n_vertex" : (10, n_vertex) "n_edge" : (15, n_edge) ... } def test_n_props(self): for cur_prop in petersen_prop: func = petersen_map[cur_prop][1] self.assertTrue(func(self.adj,**self.args) == petersen_prop[cur_prop][0]) |
编辑:
下面是使用元类为dict中的每个项添加唯一测试的方法:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | class TestMaker(type): def __new__(cls, clsname, bases, dct): # Add a method to the class' __dict__ for every key in # the petersen_prop dict. for prop in petersen_prop: dct['test_{}'.format(prop)] = cls.make_test(prop) return super(TestMaker, cls).__new__(cls, clsname, bases, dct) @staticmethod def make_test(prop): # test_wrap is the method body that will be used for each # test def test_wrap(self): func = getattr(myfuncs, prop) self.assertTrue(func(self.adj, **self.args) == petersen_prop[prop]) return test_wrap class PetersenGraph(unittest.TestCase): __metaclass__ = TestMaker |
当您运行这个时,您将为每个项目获得一个单独的测试用例。例如,在我的测试代码中,每个测试都失败了:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | ====================================================================== FAIL: test_n_edge (__main__.PetersenGraph) ---------------------------------------------------------------------- Traceback (most recent call last): File"un.py", line 26, in test_wrap petersen_prop[prop]) AssertionError: False is not true ====================================================================== FAIL: test_n_vertex (__main__.PetersenGraph) ---------------------------------------------------------------------- Traceback (most recent call last): File"un.py", line 26, in test_wrap petersen_prop[prop]) AssertionError: False is not true |
python没有从函数内部获取函数名的功能。你所能做的就是
有关详细信息,请参阅此处从该函数内确定函数名(不使用回溯)