【Python】SimplePrograms line 13 unittest
プログラム
13行プログラムです。
import unittest
def median(pool):
copy = sorted(pool)
size = len(copy)
if size % 2 == 1:
return copy[int((size - 1) / 2)]
else:
return (copy[int(size/2 - 1)] + copy[int(size/2)]) / 2
class TestMedian(unittest.TestCase):
def testMedian(self):
self.assertEqual(median([2, 9, 9, 7, 9, 2, 4, 5, 8]), 7)
if __name__ == '__main__':
unittest.main()
実行結果
Ran 1 test in 0.000s
OK
解説
「Unit testing」
個人的に興味のあった機能です。
単体テスト。
まずは、単体テストの対象となる関数「median」について把握しておきましょう。
関数「median」
最初に、引数「pool」を昇順に並べ替えます。
その後、
「pool」のサイズが奇数なら
pool[0]
pool[1]
pool[2]⇐ココの数値を出力
pool[3]
pool[4]
「pool」のサイズが偶数なら
pool[0]
pool[1]
pool[2]⇐ココと
pool[3]⇐ココの平均値を出力
pool[4]
pool[5]
関数「median」の単体テスト
テストはこちらの部分になります。
class TestMedian(unittest.TestCase):
def testMedian(self):
self.assertEqual(median([2, 9, 9, 7, 9, 2, 4, 5, 8]), 7)
class TestMedian(unittest.TestCase):
まずはこの部分。
class TestMedian(unittest.TestCase):
「unittest.TestCase」を継承して、単体テスト用のクラスを作成します。
次の行のこの部分。
def testMedian(self):
これは、テストプログラムを実行中するメンバ関数を定義します。
関数名は「test」で始まること。
でないと、テストプログラムとして実行されません。
例えば、
def utMedian(self):
のように書くと実行結果はこんな風になってしまいます。
Ran 0 tests in 0.000s
OK
「Ran 0」となって、実行されたテストは0個。
「utMedian」は実行されません。
逆に言うと、テスト用のサブ関数を作れますね。
さて、次のこの部分。
self.assertEqual(median([2, 9, 9, 7, 9, 2, 4, 5, 8]), 7)
ここがテストプログラム。
「assart」というのはプログラミングでは古くから使われている単語で、
真であれば何もしない
偽であれば警告する
という感じでしょうか。
「self.assertEqual」という記載は
一致していれば何もしない
一致していなければ警告する
ということになります。
引数は2つありますから、
2つが一致していれば何もしない
一致していなければ警告する
ということになります。
このサンプルプログラムでは、引数は次の2つ。
median([2, 9, 9, 7, 9, 2, 4, 5, 8]), 7
関数「median」を
引数「[2, 9, 9, 7, 9, 2, 4, 5, 8]」で呼び出し、
戻り値が 7 であれば何もしない
戻り値が 7 でなければ警告する
ということをしているだけです。
一見、なんだかすごいことをしていそうなのですが、例えばこんなことも書けます。
def testBoo(self):
dataa=7
self.assertEqual(dataa, 7)
dataa に 7 を設定して
dataa が 7 かどうかを確認する
それだけです。
例えばこんなことをしてみる。
import unittest
class TestMedian(unittest.TestCase):
def testBoo(self):
dataa=7
self.assertEqual(dataa, 7)
def testFoo(self):
datab=8
self.assertEqual(datab, 8)
if __name__ == '__main__':
unittest.main()
もはや、テストでもなんでもないんですが。
実行結果はこうなります。
Ran 2 tests in 0.000s
OK
2つ実行して結果はOK。
一つをNGにしてみましょう。
datab=9
にしてみます。
実行結果は・・・。
======================================================================
FAIL: testFoo (__main__.TestMedian)
----------------------------------------------------------------------
Traceback (most recent call last):
File "/storage/emulated/0/qpython/.last_tmp.py", line 8, in testFoo
self.assertEqual(datab, 8)
AssertionError: 9 != 8
----------------------------------------------------------------------
Ran 2 tests in 0.002s
FAILED (failures=1)
これでもか、というくらいのメッセージの量やなぁ。
これなら「NGを見逃しました」ということもあるまい。
うーん。
unittestって、こんなもんか。
という感じがしないでもない。
もっと便利なものを期待していたけども。
試しに、unittestを使わずに試験プログラムを書いてみる。
unittestを使って書くとこうなる。
class TestMedian(unittest.TestCase):
def testMedian(self):
self.assertEqual(median([2, 9, 9, 7, 9, 2, 4, 5, 8]), 7)
unittestを使わずに書くとこうなる。
def testMedian():
m = median([2, 9, 9, 7, 9, 2, 4, 5, 8])
if m == 7: print("ok")
else: print("ng")
うーん。
あんまり変わらん気もするけどぉ。
テストケース1つにつき1ステップで書けるから、簡単になると言えば簡単になる、かなぁ。
まずは積極的に使ってみる?
この記事が気に入ったらサポートをしてみませんか?