トランポリン関数

https://qiita.com/41semicolon/items/985bdd2f551d9392463c
https://stackoverflow.com/a/27704484/9427427
末尾再帰を逐次実行に変更する関数。
正確には末尾再帰関数を「『末尾再帰で呼び出す関数』を戻す関数」に修正した上で、それをトランポリン関数に渡して逐次実行を行ってもらう。
トランポリンというのは、横軸に時間、縦軸に呼び出しスタック階層を置いたグラフを書いたとき、再起は「ピラミッド」のようになることに対して、トランポリン関数は1階層呼び出しスタックが上がって元に戻るという動きを繰り返す「トランポリン」のような図になることから。

function countDown2 (num) {
if (num === 1) return 1;
if (num % 1000 === 0) console.log(num);
return () => countDown2(num - 1);
}

function trampoline (fn) {
return (...args) => {
let result = fn(...args);
while (typeof result === 'function') {
result = result();
}
return result;
};
}

const tramped = trampoline(countDown2);
console.log(tramped(30000)); // -> カウントダウンされ、再帰の結果の 1 が返却される