Sam*_*Rad 2 javascript recursion stack settimeout
据我从这两个答案中了解到:
当setTimeout被递归调用时,堆栈不应增长,但如果您在 FF 或 Chrome 中打开一个 devtool 并运行此函数:
function recur(n = 10) {
console.trace();
console.log(n, '++++++++++++++++');
if (n > 0) setTimeout(() => recur(--n), 1000);
}
recur()
Run Code Online (Sandbox Code Playgroud)
你会看到以下内容:
console.trace() debugger eval code:2:11
recur debugger eval code:2
<anonymous> debugger eval code:8
10 ++++++++++++++++ debugger eval code:3:11
console.trace() debugger eval code:2:11
recur debugger eval code:2
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
<anonymous> debugger eval code:8
9 ++++++++++++++++ debugger eval code:3:11
console.trace() debugger eval code:2:11
recur debugger eval code:2
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
<anonymous> debugger eval code:8
8 ++++++++++++++++ debugger eval code:3:11
console.trace() debugger eval code:2:11
recur debugger eval code:2
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
<anonymous> debugger eval code:8
7 ++++++++++++++++ debugger eval code:3:11
console.trace() debugger eval code:2:11
recur debugger eval code:2
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
<anonymous> debugger eval code:8
6 ++++++++++++++++ debugger eval code:3:11
console.trace() debugger eval code:2:11
recur debugger eval code:2
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
<anonymous> debugger eval code:8
5 ++++++++++++++++ debugger eval code:3:11
console.trace() debugger eval code:2:11
recur debugger eval code:2
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
<anonymous> debugger eval code:8
4 ++++++++++++++++ debugger eval code:3:11
console.trace() debugger eval code:2:11
recur debugger eval code:2
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
<anonymous> debugger eval code:8
3 ++++++++++++++++ debugger eval code:3:11
console.trace() debugger eval code:2:11
recur debugger eval code:2
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
<anonymous> debugger eval code:8
2 ++++++++++++++++ debugger eval code:3:11
console.trace() debugger eval code:2:11
recur debugger eval code:2
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
<anonymous> debugger eval code:8
1 ++++++++++++++++ debugger eval code:3:11
console.trace() debugger eval code:2:11
recur debugger eval code:2
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
recur debugger eval code:4
(Async: setTimeout handler)
recur debugger eval code:4
<anonymous> debugger eval code:8
0 ++++++++++++++++
Run Code Online (Sandbox Code Playgroud)
这是为什么?
Chrome 开发人员工具中的异步堆栈跟踪...旨在让您保持清醒,同时试图找出您的函数为何处于 setTimeout() 递归循环中
javascript 线程模型是事件循环。- https://flaviocopes.com/javascript-event-loop/
setTimeout()在技术上不是递归的。它是一个异步函数调用。在线程内部,它同步返回一个数字 id(您可以调用clearTimeout()它),然后作为副作用将您的函数添加到事件循环堆栈的末尾。它是一个单线程模型,所以一旦 javascript 完成了您当前的线程/事件,它就会从堆栈顶部弹出下一个函数以供执行。因此,1000 毫秒只是预定执行的最短时间,但如果它仍在执行先前的事件/线程,则可能需要更长的时间。
如果我在节点中运行此代码,我会得到:
node
Welcome to Node.js v12.5.0.
Type ".help" for more information.
> function recur(n = 10) {
... console.trace();
... console.log(n, '++++++++++++++++');
... if (n > 0) setTimeout(() => recur(--n), 1000);
... }
undefined
>
> recur()
Trace
at recur (repl:2:11)
at repl:1:1
at Script.runInThisContext (vm.js:123:20)
at REPLServer.defaultEval (repl.js:384:29)
at bound (domain.js:415:14)
at REPLServer.runBound [as eval] (domain.js:428:12)
at REPLServer.onLine (repl.js:700:10)
at REPLServer.emit (events.js:205:15)
at REPLServer.EventEmitter.emit (domain.js:471:20)
at REPLServer.Interface._onLine (readline.js:314:10)
10 ++++++++++++++++
undefined
> Trace
at recur (repl:2:11)
at Timeout._onTimeout (repl:4:31)
at listOnTimeout (internal/timers.js:531:17)
at processTimers (internal/timers.js:475:7)
9 ++++++++++++++++
Trace
at recur (repl:2:11)
at Timeout._onTimeout (repl:4:31)
at listOnTimeout (internal/timers.js:531:17)
at processTimers (internal/timers.js:475:7)
8 ++++++++++++++++
Trace
at recur (repl:2:11)
at Timeout._onTimeout (repl:4:31)
at listOnTimeout (internal/timers.js:531:17)
at processTimers (internal/timers.js:475:7)
7 ++++++++++++++++
Trace
at recur (repl:2:11)
at Timeout._onTimeout (repl:4:31)
at listOnTimeout (internal/timers.js:531:17)
at processTimers (internal/timers.js:475:7)
6 ++++++++++++++++
Trace
at recur (repl:2:11)
at Timeout._onTimeout (repl:4:31)
at listOnTimeout (internal/timers.js:531:17)
at processTimers (internal/timers.js:475:7)
5 ++++++++++++++++
Trace
at recur (repl:2:11)
at Timeout._onTimeout (repl:4:31)
at listOnTimeout (internal/timers.js:531:17)
at processTimers (internal/timers.js:475:7)
4 ++++++++++++++++
Trace
at recur (repl:2:11)
at Timeout._onTimeout (repl:4:31)
at listOnTimeout (internal/timers.js:531:17)
at processTimers (internal/timers.js:475:7)
3 ++++++++++++++++
Trace
at recur (repl:2:11)
at Timeout._onTimeout (repl:4:31)
at listOnTimeout (internal/timers.js:531:17)
at processTimers (internal/timers.js:475:7)
2 ++++++++++++++++
Trace
at recur (repl:2:11)
at Timeout._onTimeout (repl:4:31)
at listOnTimeout (internal/timers.js:531:17)
at processTimers (internal/timers.js:475:7)
1 ++++++++++++++++
Trace
at recur (repl:2:11)
at Timeout._onTimeout (repl:4:31)
at listOnTimeout (internal/timers.js:531:17)
at processTimers (internal/timers.js:475:7)
0 ++++++++++++++++
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
172 次 |
| 最近记录: |