品質とひきかえに犠牲になるもの |
作成日:2001-03-27 最終更新日: |
あるプロジェクトのソースプログラムを見る必要に迫られて見ていたところ、 とんでもない書き方をしているところがあった。 やりたいことは、1から100までの数字を無作為に(ランダムに)5個選ぶことである。 5個の順番も無作為である(小さい順とか、大きい順ではない)。 さあ、どうするか。 1から100までの乱数(ランダムな数)を発生するサブルーチンは使えるものとする。 サブルーチンということばがわからなければ、 1から100まで100種類の目がある電子さいころとでも思って下さればいい。
これを、ふつうに、素朴に考えたらどうするだろう。ふつうは次のように考えるだろう。
これは、正しい答えを出す。しかし、なんとなく野暮な感じがする。 下手をすれば何度もサブルーチンを走らせてしまう(サイコロをふってしまう)ようだ。 この方法を使う時、サブルーチンを走らせる回数(サイコロをふる回数)を求めるのは もっとかっこいい方法はないだろうか。
選ぶ5個の数値が小さい順でよいなら、こんな方法がある。m = 5, n = 100 とする。
なんのことかわからないだろう。この手続きがうまくいく理由を説明することは少し難しい。
サブルーチンの呼び出し回数を少なくするとか、選ぶ5個の数値の大小の順もランダムにしたいとか、 いろいろなことが考えられる。そうして、それぞれ対応した考え方(アルゴリズム)は存在する。 たとえば、呼び出し回数についていえば、選ぶ回数だけで答えが決まるアルゴリズムはある。
わたしは最初、とんでもない書き方をしているプログラム、といった。 それは、一番最初に紹介した素朴なプログラムである。 今は100個から5個を選んでいるが、 このどちらも変わった時、特に選ぶ個数が変わった時の拡張性がない。 また、サブルーチンは呼ばれる回数が少なければ少ないほどいい。
ところが、とんでもない書き方で一点だけいいことがある。 それは「何をやっているかわかる」のである。 「数が小さい順に出てもいいのなら」で紹介した方法は、なぜそれでうまくいくのか、 という問いに答えようとすると時間がかかる。すなわち、 高校の確率ぐらいの知識と理解力が必要になる。 それに比べば、素朴な書き方は考えている通りにプログラムを書いているだけのことである。 何かプログラムに問題があったとしても、 それを見る人にとってわかりやすいという利点はある。
つまり、計算の主要品質である効率性を追求するあまり、 別の主要品質である保守性が損なわれることもありうる、 というのがいいたいことである。ただし、今挙げた程度の例では、 保守性を損なうほどの複雑さはない。
もっともいいのは、よいアルゴリズムを使い、なおかつ説明を十分行うことである。 よいアルゴリズムが紹介されている参考文献を掲げる。
ベントレーの本はアルゴリズムのみが示されている(コラム13)。 奥村の本には、 ベントレーの本で示されたアルゴリズムをC言語に翻訳した例が示されている。 ただし順序のランダム性については無視している。
実はこのページの制作と並行して、 JavaScript により上記アルゴリズムを実装していた。 その過程はランダム順列というページに記した。 なんと、私はバグのあるアルゴリズムを公開してしまったのだ。 つまり、実装も難しい、ということになる。 これの対策は、一つはテストをきちんと行う、ということだろう。 それから、関数の特性を正しく把握する、というのも反省点である。 (この項、2010-05-16 追加)
まりんきょ学問所 > 品質の部屋 > 品質とひきかえに犠牲になるもの