【问题标题】:flow of execution of javascript(synchronous or asynchronous)javascript的执行流程(同步或异步)
【发布时间】:2015-12-19 07:37:38
【问题描述】:

谁能解释一下以下代码和javascript的行为

for(var i = 0; i < 5; i++)
{
    setTimeout(function(){
    document.write('Iteration ' + i + ' <br>');
    },1000);
}

document.write('DONE!');

为什么打印“完成!”第一的? 它不应该打印循环的所有值然后打印'DONE!'吗?

【问题讨论】:

  • '完成!' for-loop 完成后正在打印..
  • 流程是你先设置5个超时函数,然后打印完成——按顺序完成。函数在间隔后执行,这就是为什么先打印 done 的原因,但程序的流程是第一个动作是设置 5 个超时回调。

标签: javascript asynchronous synchronous


【解决方案1】:

正常的 Javascript 是 Synchronous 逐行执行,但通过代码更改,您有时可以作为异步执行,但它实际上不会在单独的线程上执行。

好的,如果你想在 Document.write 完成后打印Done 怎么办

length = 0;
for(var i = 0; i < 5; i++)
{
  setTimeout(function(index){
  console.log('Iteration ' + index + ' <br>');
  length++;
  callback();
  }(i),1000);
}

function callback(){
 if(length == 5)
   console.log('DONE!');
}

我们在这里所做的是递增计数器,并在每次递增后尝试调用回调,当计数器达到 5 时,这意味着所有 5 个函数都被调用,然后我们能够打印 Done

作为一个侧面和重要的说明,您试图打印 0, 1, 2, 3, 4 但实际上当您运行代码时,它会给您 5, 5, 5, ,5, 5 因为您写 @ 987654325@ 和 i 在您打印时达到 5,这就是它退出 for 循环的原因,但您注意到我添加的代码,我将 i 作为参数传递给函数,以便保存我们的值以及执行函数的时间将写入 0, 1, 2, 3, 4

【讨论】:

    【解决方案2】:

    为什么打印“完成!”第一的?它不应该打印循环的所有值然后打印'DONE!'吗?

    不,您已经明确告诉它不要这样做;相反,您刚刚创建了五个函数并调用了五次 setTimeout 以将它们提供给浏览器以便稍后调用。

    这段代码:

    setTimeout(function(){
    document.write('Iteration ' + i + ' <br>');
    },1000);
    

    调用函数setTimeout,传入你看到的函数。该函数当时被调用。它刚刚创建。 setTimeout稍后会调用它,就像它的工作一样。 (当它这样做时,它会炸掉文档,因为在页面的主要解析完成后调用document.write 会隐式执行document.open,这会清除之前的文档。)

    以下是该代码发生的情况:

    1. 变量i 已创建。
    2. 设置为0
    3. 创建了一个函数。
    4. 调用 setTimeout 时传入该函数对象的引用以及值 1000
    5. i 递增。
    6. 1234i)的值重复第 2 步到第 5 步。
    7. document.write 使用值 'DONE!' 调用
    8. 大约一秒钟后,浏览器调用循环中创建的第一个函数。
    9. 该函数调用document.write,它隐式执行document.open,将现有文档吹走并替换为Iteration 5 &lt;br&gt;(是的,真的是5)。
    10. 循环中创建的第二个函数运行,再次输出消息。
    11. 调用其余三个函数,将消息再添加 3 次。

    我们看到Iteration 5 五次而不是Iteration 0,然后是Iteration 1 等的原因是这些函数对变量 i 有一个持久的引用,而不是它在创建时的值,所以它们都在稍后读取它的值,直到它们运行时。

    【讨论】:

    • 请参考这个帖子并检查答案2:stackoverflow.com/questions/16523870/…
    • @ProblemSolver:不确定您要在此处说什么,但请注意,并非每个人都以相同的顺序看到答案。如果您想参考特定答案,请使用其下方的“共享”链接来获取指向该特定答案的链接。但我没有看到上面未涵盖的任何相关内容。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-12-05
    • 2012-02-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多