「再帰を使うとコードがぐっと短くなる」実例をいくつか紹介します。ループで書くとゴチャゴチャする処理が、再帰だとスッキリ書けるのが魅力です。
実例1:ネストした配列を平らにする(flatten)
ループで書くと…
function flattenLoop(arr) {
let result = [];
let stack = [...arr];
while (stack.length > 0) {
const item = stack.pop();
if (Array.isArray(item)) {
stack.push(...item); // 配列なら展開してまた積む
} else {
result.unshift(item); // 順番を保つために先頭に追加
}
}
return result;
}
console.log(flattenLoop([1, [2, [3, 4]], 5])); // [1,2,3,4,5]
JavaScript→ スタックを使ったり unshift したりで、ちょっと複雑。
再帰で書くと…
function flattenRec(arr) {
let result = [];
for (const item of arr) {
if (Array.isArray(item)) {
result = result.concat(flattenRec(item)); // 再帰で展開
} else {
result.push(item);
}
}
return result;
}
console.log(flattenRec([1, [2, [3, 4]], 5])); // [1,2,3,4,5]
JavaScript👉 再帰版は直感的で短い!
「配列ならもう一度 flatten、そうでなければ push」だけで済む。
実例2:フォルダ内のファイル一覧を表示
再帰版(シンプル)
function showFiles(folder) {
for (const item of folder) {
if (Array.isArray(item)) {
showFiles(item); // サブフォルダなら再帰
} else {
console.log(item);
}
}
}
const myFolder = ["file1.txt", ["sub1", ["deep.txt"]], "file2.txt"];
showFiles(myFolder);
// file1.txt
// sub1
// deep.txt
// file2.txt
JavaScript→ ループだけで深さ不明のフォルダを処理しようとすると、深さごとにネストした for 文が必要になり、コードが長くなる。再帰なら「中にフォルダがあればもう一度呼ぶ」だけで完結。
実例3:文字列の反転
ループ版
function reverseLoop(str) {
let result = "";
for (let i = str.length - 1; i >= 0; i--) {
result += str[i];
}
return result;
}
console.log(reverseLoop("hello")); // "olleh"
JavaScript再帰版
function reverseRec(str) {
if (str === "") return "";
return reverseRec(str.slice(1)) + str[0];
}
console.log(reverseRec("hello")); // "olleh"
JavaScript👉 再帰版はわずか2行で書ける!
「残りを反転 + 先頭を最後に付ける」という発想でシンプル。
まとめ
- 再帰は「入れ子構造」や「分割できる問題」に強い。
- ループで書くと長くなりがちな処理も、再帰だと短く直感的に書ける。
- 特に「配列のネスト処理」「ツリー構造の探索」「文字列操作」などで効果的。
