← メディア一覧

再帰:パズルを「それ自身」で解く技術

7分25秒 | アルゴリズム基礎FE

基本情報技術者試験の頻出テーマを解説した動画コンテンツです。

トランスクリプト(字幕テキスト)

こんにちは。自分自身を呼び出す。なんだか哲学みたいですよね。でもこれ、プログラミングの世界ではめちゃくちゃ強力なテクニックなんです。 今日はこの再帰、つまりパズルをそれ自身で解いちゃうっていう、ちょっと不思議で、でもすごくエレガントな考え方の核心に迫っていきましょう。 さて、早速ですが、多くの人が最初にこう思うはずです。え、関数が自分を呼び出すって?それってただの無限ループじゃないの?って。 うん、確かにそう聞こえますよね。下手をすると、プログラムがクラッシュするまで止まらないみたいな、ちょっと危ない感じがしますよね。 そう、ここが一番の謎なんです。もし関数が自分自身を呼び出し続けるんだとしたら、一体どうやって、そして、いつ止まるんでしょうか? このミステリーを解き明かすことこそが、再帰を理解するための、もう本当に最初の、そして最大の鍵なんです。 実は、この二つには、決定的でものすごく大事な違いがあるんです。左側の無限ループ。こいつには出口がない。もう、システムが悲鳴を上げるまで永遠に走り続けます。 でも、右側の再帰は違うんです。必ず、ここまで来たらおしまいっていう停止条件、つまり明確な出口がちゃんと設計されているんですね。ここがポイントです。 じゃあ、この出口があるっていう感覚、どうやって掴んだらいいんでしょうか?ここで、すごくわかりやすい例え話があります。それがこのマトリョーシカ人形です。 この入れ子構造をイメージすると、再帰の仕組みが一気にクリアになりますよ。 さあ皆さんも、一緒に考えてみてください。このマトリョーシカ、どうやって開けますか?まず、一番大きな人形をパカッと開けますよね。すると中から、 あ、一回り小さい、そっくりな人形が出てきた。さあ、どうしましょう? そうですよね。やることはまったく同じ。その小さな人形も同じように開けるんです。これを、もうこれ以上開けられない、中身が詰まった人形にたどり着くまで、 ひたすら繰り返す。ただそれだけなんです。 そしてついに、もうこれ以上開けられないってなった瞬間、それこそが出口なんです。これが停止条件。 この最後の一個があるから、この作業は無限に続かない。安心して同じことを繰り返せる。いわば命綱みたいなものなんですね。 さて、このマトリョーシカみたいな入れ子の考え方、じゃあ、実際にどう役立ってるのって話ですよね。実はこれ、ものすごくパワフルで、 最も有名な応用例の一つが、あのクイックソートっていうアルゴリズムなんです。これはまさに、再帰の力を最大限に引き出した、超高速な並べ替えの方法なんですよ。 クイックソートって、一体何を刷るものなのか。すごく簡単に言うと、バラバラに並んだ大量のデータを、あっという間にきれいに整列させるアルゴリズムです。 そのやり方が面白くて、まず、大きなデータの塊を二つの小さなグループに分ける。そして、その小さなグループそれぞれに、 「はい、君たちも自分で自分を並べ替えてね」って、まったく同じ仕事を丸投げするんです。再帰的に、ですね。 この仕組み、本当にマトリョーシカそっくりだと思いませんか?まず、ステップ1「分割」です。基準となる値を一つ選んで、それより小さいグループと大きいグループに分けます。 で、ステップ2。ここが再帰の魔法です。分けたそれぞれのグループに、今やったのと同じやり方で「君たちも自分をソートして」って、自分自身の分身に仕事を任せる。 そして大事なステップ3「停止」。グループの中身がデータ一個だけになったら、もう並べ替える必要ないですよね。そう、これがあのマトリョーシカの一番小さい人形、ここが出口なんです。 でも、ここでまた新しい疑問が湧いてきませんか?こんなに次から次へと自分を呼び出していて、コンピューターは混乱しないんでしょうか? あれ、今どの仕事の途中だっけ?終わったらどこに戻ればいいんだっけ?って、迷子になっちゃいそうですよね。 その秘密を解く鍵が、スタックっていう仕組みにあります。ちょっと想像してみてください。机の上に透明なレンガを積み上げていくイメージです。 関数が呼び出される、つまり新しい仕事が始まるたびに、この積み上がったレンガの一番上に、新しいレンガが一つ、ポンと置かれるんです。 まさにこのスライドのイメージですね。まず、元の大きなリストをソートせよという最初の仕事が来ると、土台になるレンガが一つ置かれます。 次にその仕事が、「じゃあ、まず小さい方の半分から片付けよう」と自分を呼び出すと、その上に二つ目のレンガが積まれる。 さらにその中でもっと小さいグループを、ってなると、三つ目のレンガがその上に。こんなふうに、仕事が入れ子になるたびに、レンガの塔がどんどん、どんどん高くなっていくわけです。 そして、一番てっぺんの一番小さな仕事が終わった瞬間、つまりあの出口にたどり着いたとき、何が起きるか。一番上のレンガがスッと取り除かれるんです。 すると、その一つ下にあったレンガ、つまり中断していた仕事が顔を出す。プログラムはそこに戻って作業を再開するんです。 こうやって積み上げた仕事を上から順番に一つずつ片付けて、最終的に一番最初の場所まで戻ってくる、というわけなんですね。 さあ、だんだん全体像が見えてきましたね。ここまでの話をまとめると、再帰の最も重要なポイントはこれです。自己委任の技術。 つまり、難しい問題を賢く他の誰か、この場合は小さな自分に任せる技術なんです。 これが再帰を使いこなすためのエッセンスです。レシピみたいなものですね。第一に、何よりもまず、出口、つまり停止条件を見つけること。 第二に、大きな問題をそれとそっくりな、でももっと簡単な小さな問題に分割する。 第三に、その小さな問題を解決してくれるプロセスを、もう信じて任せちゃう。 そして最後に、それぞれの小さな問題から返ってきた答えをガチャンと組み合わせれば、あら不思議。元の大きな問題が解けているというわけです。 この言葉が、再帰の考え方を本当によく表していますよね。再帰とは、大きな問題を解決するために、小さな自分たちにその一部を解決させる技術である。 一見すると魔法みたいですけど、その裏側には、すごく論理的で美しい問題解決のアプローチがあるんです。 さて、この考え方のパターン、少しは掴めたでしょうか?じゃあ最後に皆さんに質問です。このパターンを理解したいま、あなたの身の回りにある複雑な問題、 例えば仕事の大きなプロジェクトとか、何か新しいスキルを学ぶプロセスとか、そういうものにこの「そっくりな小さなパーツに分割して解決する」っていう考え方、応用できそうだと思いませんか? 再帰っていうのはただのプログラミング技術じゃない。物事の見方を変える強力な思考ツールでもあるんです。

このコンテンツは Web society で視聴・学習できます。