単純バグなんて解決済みの問題だ

前回言及したような

if (value = expected)

と間違って書いてしまう類のバグがある。設計ミスとか勘違いとか調査不足とかでなくて、単純に書き間違えたことによるバグである。こういうのを単純バグと呼ぶならば、単純バグなんてもう世の中では解決済みの問題である。

解決方法は簡単だ。ユニットテストを書けばよい。

全ルートを通して動作が確認できれば正しさは保証される。作りたかったルーチンが正しいのかはわからないが、作ろうとしていたルーチンができていることは保証される。

コードが間違っていて、テストが正しければNGとなる。コードが正しくて、テストが間違っていてもNGとなる。両方が間違っていたらそれもNGとなる。なぜならば、コードもテストも同じように間違う可能性なんて無視できるからだ。間違い方が取りうる値は極めて多い。2つのコードが同じように間違うなんて可能性は無視していいほど小さい。両方が同じように間違っているなら、それは作ろうとしているものを勘違いしていたときだけだ。これは単純バグではない。

したがって、ユニットテストをすべてのルートについて書けば、作ったルーチンは作ろうとしたものになっている。

銀の弾丸なんてないとはいうが、ユニットテストを書くことについてはある種のバグを確実になくせる魔法のプロセスだ。JUnit等のユニットテストを書くための道具は揃っている。ここまでお膳立てされていてやらない理由がない。

ユニットテストを書くことには副次的な効果もある。

コードが綺麗になる。テストが書けないコードというのは部品化されていない。テストを書きやすいようにコードを書いたら、自ずとルーチンが部品化される。また、コードが動くようになったあとに、きれいに直すことも簡単である。再度テストを実行して壊れていないことを確認すれば良いだけだ。コードを直す際の障害が少ない。

また、テストコードは仕様書の代わりにもなる。コードだけでは何をしたいのか分からなくても、コメントと変更履歴に加えてテストが残っていればコードの意図をが分かるようになる。こういう時にこういう動きをするべきというのを規定したものがテストコードであり、これは仕様書と同じものだ。だからテストコードも理想を言えば人間が読めるようになっていた方がよい。汚くてもないよりはましだ。

こんなの当たり前のことだと思うのだけれど……

JUnit実践入門 ~体系的に学ぶユニットテストの技法 (WEB+DB PRESS plus)

JUnit実践入門 ~体系的に学ぶユニットテストの技法 (WEB+DB PRESS plus)