web前端技术分享

js执行机制,同步-异步,宏任务-微任务

2019-04-15  本文已影响0人  一刀一个小黄鱼

同步和异步任务

由于JavaScript是一门单线程语言,是这门语言的核心特征。

单线程就意味着,所有任务需要排队,前一个任务结束,才会执行后一个任务。如果前一个任务耗时很长,后一个任务就不得不一直等着。为了解决这个问题,设计者把执行的任务分成两种:同步任务、异步任务

1.png
// 首先打印1
console.log(1); 

// 进入到Event Table,注册了回调函数打印2开始执行,2s后进入到Event Queue;
setTimeout(() => { 
  console.log(2);
},2000)

// 也进入到Event Table,请求成功后执行函数进入到Event Queue
$.ajax({
    url:www.javascript.com,
    data:data,
    success:() => {
      console.log('3');
    }
})

// 继续执行主线程中的任务,打印3,执行完所有的主线程任务后,在去Event Queue的任务
console.log(4);

// 1 4 2 3 也可能是1 4 3 2 (根据ajax请求的时间是否快于setTimeout)

宏任务与微任务

除了广义的同步任务和异步任务,我们对任务有更精细的定义

不同类型的任务会进入对应的事件队列中,比如setTimeoutsetInterval会进入相同的事件队列。

事件循环的顺序,决定js代码的执行顺序。进入整体代码(宏任务)后,开始第一次循环。接着执行所有的微任务。然后再次从宏任务开始,找到其中一个任务队列执行完毕,再执行所有的微任务。

2.png
console.log(1);

setTimeout(() => {
  console.log(2);
},100)

new Promise(resolve => {
  console.log(3);
  resolve()
}).then(res => {
  console.log(5);
})

console.log(6);

// 1 3 6 5 2

总结

一个js的执行顺序,可以理解为先分为同步和异步,再划分为宏任务还是微任务。但这2者是没有关系的

setTimeout(() => {
  // 宏任务
  new Promise(resolve => {
    console.log('1');
    resolve();
  }).then(() => {
    // 微任务
    console.log('2');
  });
    
  // 宏任务
  console.log('3');
  
  // 宏任务
  setTimeout(() => {
    process.nextTick(function() {
      console.log('4');
    })
    
    console.log('5');
  }, 1000)
}, 1000);

//1s后执行顺序为1 3 2 5 4

参考来之于这篇文章

上一篇 下一篇

猜你喜欢

热点阅读