【问题标题】:Does the JS debugger suspend the whole JS event loop?JS 调试器是否暂停整个 JS 事件循环?
【发布时间】:2012-07-19 19:40:55
【问题描述】:

我有一些非常奇怪的行为。我有以下 JQuery:

myElement.fadeOut(100);

存在某种竞争条件,因此元素最终不会被隐藏。如果我在该行上放置一个调试器并单步执行代码,它工作正常并且元素淡出并被隐藏。称它为Heisenbug

我的问题不是关于比赛条件本身。我想知道考虑到 JavaScript 运行时的性质,这怎么可能发生。据我了解,以下谓词是正确的:

  1. fadeOut() 由 JQuery animate() 实现
  2. animate() 由一系列setTimeout() 调用实现
  3. setTimeout() 安排在某个时间点执行队列中的函数
  4. 当事件到达队列的开头时,函数被执行。
  5. 只有一个事件循环,按顺序执行。
  6. 在任何给定时间点,只有一个通过调用堆栈的函数/路径正在执行。

鉴于我正在调试器中单步执行一个函数,因此必须暂停执行,并且不能执行其他函数。

我看不出在这种情况下怎么可能出现竞争条件。 您能否建议调试代码和非调试代码之间的执行有何不同?

【问题讨论】:

    标签: javascript debugging javascript-debugger


    【解决方案1】:

    您的要点是正确的,除了使用requestAnimationFrame() 而不是setTimeout()(如果浏览器支持)。

    例如,如果 myElement 是由 AJAX 调用异步创建的,但 fadeOut() 在不等待请求完成的情况下被调用,则调试会话可能会对代码的行为产生影响。

    在这种情况下,手动单步执行代码可以为请求返回和在调用 fadeOut() 之前创建的元素留出足够的时间,而在正常情况下请求不会返回。

    【讨论】:

    • 使用成功或完成回调,而不是超时,如果这是正在发生的事情。总是假设 ajax 可能会挂起。
    • 我肯定没有为此使用超时!
    猜你喜欢
    • 2014-04-09
    • 1970-01-01
    • 1970-01-01
    • 2021-03-25
    • 1970-01-01
    • 2018-06-03
    • 1970-01-01
    • 1970-01-01
    • 2013-08-20
    相关资源
    最近更新 更多