vue2.x($nextTick)

this.$nextTick平时怎么使用的?说说它的原理?

① vue的DOM更新是异步更新的(为什么设计成异步更新?因为比如我们在created钩子函数里面100次循环设置this.xxx=i,若不是异步那岂不是需要触发100次响应dom更新,这里也是优化方案之一),比如我们在执行了this.xxx=1,这个时候去拿dom上的xxx值结果还是原来的值而非刚刚设置的1,此时我们需要使用this.$nextTick在callback中拿就没问题了

② 原理:

源码1905~源码2007行
源码1984行 执行nextTick后会将cb全部Push进callbacks全局数组收集任务起来
源码1999行 这里执行了一个timerFunc函数 这个声明过程在源码1930行到1982行 这里作了
		  1.是否支持Promise         浏览器方法兼容
          2.是否支持MutaionObserver DOM监听方案 
          3.是否支持setImmediate 	Node环境 
          4.最后使用setTimeout(flushCallbacks,0) 做了这么多判断其实是利用了js事件循		   			   环(event loop)机制来将当前需要执行的cb放到事件任务队列中 在下一次事件循环中再执行             后面会记录下事件循环相关东西
源码1910行 这里使用for循环分别来执行之前push进来的函数(也就是我们cb回调)     
js事件循环Event Loop是基于js是单线程操作 同一时间只能执行一个任务 而js主线程拥有一个“执行栈”以及一个“任务队列” 参考网上说法:js执行主线程任务 遇到需要执行异步任务时会将此刻的异步任务推进“任务队列”,当主线程执行完毕后会“清空当前执行栈”,按照先入先出的顺序来执行任务队列里面的任务
   异步任务分为:宏任务(macrotasks)和微任务(microtasks)
	 宏任务(macrotasks)一般包含:
     	1.I/O操作                浏览器支持      node支持
        2.setTimeout            浏览器支持      node支持
        3.setInterval           浏览器支持      node支持
        4.setImmediate          浏览器不支持     node支持
        5.requestAnimationFrame 浏览器支持      node不支持
     微任务(microtasks)一般包含:
        1.process.nextTick      浏览器不支持    node支持
        2.MutationObserver      浏览器支持      node不支持
        3.Promise.then catch finally 浏览器支持 node支持
        4.async await           浏览器支持      node支持
例如1:
console.log('script start');
setTimeout(function() {
  console.log('setTimeout');
}, 0);
Promise.resolve().then(function() {
  console.log('promise1');
}).then(function() {
  console.log('promise2');
});
console.log('script end');

我的理解是这4句代码整体是一个js主线程 从上往下执行
第一句:打印出"script start"
第二句:遇到异步任务且setTimeout属于宏任务 压入异步任务宏队列(若存在多个则按先入先出)
第三句:遇到异步任务且Promise属于微任务 压入异步任务微队列(若存在多个则按先入先出)
第四句:打印出"script end"
至此js主线程上task执行完毕 那么需要执行异步任务 而异步任务中微任务先于宏任务执行
	   打印出"promise1"
       打印出"promise2"
最后执行宏任务 打印出"setTimeout"
例如2:
console.log('script start');
setTimeout(function() {
  console.log('setTimeout1');
}, 0);
setTimeout(function() {
  console.log('setTimeout2');
}, 0);
Promise.resolve().then(function() {
  console.log('promise1');
  Promise.resolve().then(function(){
      console.log('promise内部')
  })  
}).then(function() {
  console.log('promise2');
}).then(function(){
  console.log('promise3')
});
console.log('script end');
// script start
// script end
// promise1
// promise内部
// promise2
// promise3
// setTimeout1
// setTimeout2
例如3new Promise(resolve => {
 resolve();
})
 .then(() => { // 4行
     new Promise(resolve => {
     	resolve();
     })
     .then(() => {
     	console.log(777); // 9行
     })
     .then(() => {
     	console.log(888); // 12行
     });
 })
 .then(() => {
 	console.log(666); // 16行
 });
这种嵌套promise可以这样理解 程序先执行第一个promise.then即第4行(压入队列16行) 接到遇到promise.then该分支没的其他主代码执行 则执行promise.then即第9行(压入队列12行) 执行完后又返回来执行promise.then的第二个即16行 然后再执行内部的第二个promise.then即12// 777
// 666
// 888
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值