世界中のデバッグが下手なキミへ。書いている時間より直している時間の方がずっと長く、本当はこの職業を選んではいけなかったかも知れないキミへ。
デバッグというプロセスは、仮説と検証の繰り返しでできている。根拠に基づいた仮説を立て、その仮説を正しく検証し、外れたらまた別の根拠に基づいた仮説を立てる。その繰り返しを我々はデバッグと呼んでいる。
ところがどうやらキミは、それを知らないようだ。かわいそうに、だれも教えてくれなかったのだろう。アタシもそういえば、後輩たちにこういうことをきちんと教えた覚えがない。まぁ…ちょっとは「ゴメン」だな。
キミのデバッグ(に、なっていないんだがね。見ていると)は、バグという怪物に武器を持たずに目をつぶり、ただ突進していくようなものだ。あちこち手当たり次第に押したり突いたりしているようだが、それでバグが直ったらそれはまぐれというものだ。直したのではなく、直ったと言うべきだ。
まずは落ち着いて、現象をよく見ることだ。なにが起きているのか、あるいはなにが起きていないのか、期待と違っているところを冷静に、何度も何度も観察する。
そうしているうちに、こうなっている原因はこれではないか…という仮説が浮かんでくる。自分が書いたプログラムだもの、わからないはずはない。他人が書いたものであっても、少なくとも該当する部分を何度も読んで理解していたら、仮説は立てられるものだ。
仮説が立ったら、それを検証してみよう。いきなりプログラムに手を突っ込まなくても検証できる場合がある。たとえば「この仮説が正しければ、ここでプログラムにこういうデータを食わせるとこうなるはずだ」とわかる場合もあるからだ。
それができない場合はプログラムの該当部分に手を入れるが、「いまデバッグのためにここに手を入れている」ということがわかるようなコメントを書いておくことを忘れないように。不幸にして仮説が正しくなかった場合は速やかにその部分を元に戻しておくことが(あとの混乱を避けるために)必要だが、コメントはそのために有効だ。
これを何度か繰り返すと、原因はかなり絞られてくる。絞られてきたと感じたら作業をいったん止めて休憩するといい。熱くなった頭をちょっと冷やして、その先の作業でミスを起こさないようにするためだ。慌てることはない。「ゴールは近づいてる」(ZARD)のだから。
エディタを開いてプログラムを突き廻すのは、よく観察して仮説を立ててからのことだ。デバッグのために朝から晩までキーボードを叩き続けているのはプロじゃなくてセミプロ。え? なんでセミプロ? そりゃ、朝から晩までキー(木)にしがみついて、オシッコの時だけ離れるから、蝉みたいなもんだろ。だからプロじゃなくてセミプロ。
まぁ下手な冗談はともかくとして、これがデバッグの正しいやり方。見つめたり考えたりという時間をかけるのはまどろっこしいのだろうが、結局はこのやり方の方が作業時間は短くてすむ。慣れてくると、他人のデバッグ作業でも現象を聞いただけで原因がわかることもある。そうなるように自分の頭を鍛えていくわけだ。
アタシにこのやり方を教えてくれたのは、いまでも師と仰ぐ天才プログラマK氏だ。
そのときのことはよく覚えているが、狭い部屋で背中合わせで作業をしていたときのことだ。腕ずくデバッグをしていた若き日のアタシがバグ取りに苦戦しており、ときどきぶつぶつと独りごとを言っていた。師はいきなり振り向くと、説明するときのクセでアタシの目の前に人差し指を立ててこう言った。
「仮説その1。○○変数を初期化していない」。
アタシは負けずに返す。
「○○変数が初期化されていなければ、そもそもここには来ない」。
師は続けて、
「うーん…仮説その2。○○変数に足し込む値を間違えている」。
アタシ「そんな、、、あーっっっ」。
師「勝った」。(師よ、勝ち負けの問題ですか?)
それ以来社内では、この「仮説その1」が大流行した。師はゲームのようにして、この手法をアタシに伝授してくれたのだった。おかげでプログラマを廃業せずにすんだわけで、ありがたいことなのだった。
ということで「腕ずく派」の諸君。デバッグは仮説と検証の繰り返しである。努々(ゆめゆめ)忘れることなかれ。
デバッグというプロセスは、仮説と検証の繰り返しでできている。根拠に基づいた仮説を立て、その仮説を正しく検証し、外れたらまた別の根拠に基づいた仮説を立てる。その繰り返しを我々はデバッグと呼んでいる。
ところがどうやらキミは、それを知らないようだ。かわいそうに、だれも教えてくれなかったのだろう。アタシもそういえば、後輩たちにこういうことをきちんと教えた覚えがない。まぁ…ちょっとは「ゴメン」だな。
キミのデバッグ(に、なっていないんだがね。見ていると)は、バグという怪物に武器を持たずに目をつぶり、ただ突進していくようなものだ。あちこち手当たり次第に押したり突いたりしているようだが、それでバグが直ったらそれはまぐれというものだ。直したのではなく、直ったと言うべきだ。
まずは落ち着いて、現象をよく見ることだ。なにが起きているのか、あるいはなにが起きていないのか、期待と違っているところを冷静に、何度も何度も観察する。
そうしているうちに、こうなっている原因はこれではないか…という仮説が浮かんでくる。自分が書いたプログラムだもの、わからないはずはない。他人が書いたものであっても、少なくとも該当する部分を何度も読んで理解していたら、仮説は立てられるものだ。
仮説が立ったら、それを検証してみよう。いきなりプログラムに手を突っ込まなくても検証できる場合がある。たとえば「この仮説が正しければ、ここでプログラムにこういうデータを食わせるとこうなるはずだ」とわかる場合もあるからだ。
それができない場合はプログラムの該当部分に手を入れるが、「いまデバッグのためにここに手を入れている」ということがわかるようなコメントを書いておくことを忘れないように。不幸にして仮説が正しくなかった場合は速やかにその部分を元に戻しておくことが(あとの混乱を避けるために)必要だが、コメントはそのために有効だ。
これを何度か繰り返すと、原因はかなり絞られてくる。絞られてきたと感じたら作業をいったん止めて休憩するといい。熱くなった頭をちょっと冷やして、その先の作業でミスを起こさないようにするためだ。慌てることはない。「ゴールは近づいてる」(ZARD)のだから。
エディタを開いてプログラムを突き廻すのは、よく観察して仮説を立ててからのことだ。デバッグのために朝から晩までキーボードを叩き続けているのはプロじゃなくてセミプロ。え? なんでセミプロ? そりゃ、朝から晩までキー(木)にしがみついて、オシッコの時だけ離れるから、蝉みたいなもんだろ。だからプロじゃなくてセミプロ。
まぁ下手な冗談はともかくとして、これがデバッグの正しいやり方。見つめたり考えたりという時間をかけるのはまどろっこしいのだろうが、結局はこのやり方の方が作業時間は短くてすむ。慣れてくると、他人のデバッグ作業でも現象を聞いただけで原因がわかることもある。そうなるように自分の頭を鍛えていくわけだ。
アタシにこのやり方を教えてくれたのは、いまでも師と仰ぐ天才プログラマK氏だ。
そのときのことはよく覚えているが、狭い部屋で背中合わせで作業をしていたときのことだ。腕ずくデバッグをしていた若き日のアタシがバグ取りに苦戦しており、ときどきぶつぶつと独りごとを言っていた。師はいきなり振り向くと、説明するときのクセでアタシの目の前に人差し指を立ててこう言った。
「仮説その1。○○変数を初期化していない」。
アタシは負けずに返す。
「○○変数が初期化されていなければ、そもそもここには来ない」。
師は続けて、
「うーん…仮説その2。○○変数に足し込む値を間違えている」。
アタシ「そんな、、、あーっっっ」。
師「勝った」。(師よ、勝ち負けの問題ですか?)
それ以来社内では、この「仮説その1」が大流行した。師はゲームのようにして、この手法をアタシに伝授してくれたのだった。おかげでプログラマを廃業せずにすんだわけで、ありがたいことなのだった。
ということで「腕ずく派」の諸君。デバッグは仮説と検証の繰り返しである。努々(ゆめゆめ)忘れることなかれ。