亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

小白,請教各位大佬!求大佬解釋下下面這段代碼的執行順序

小白,請教各位大佬!求大佬解釋下下面這段代碼的執行順序

繁花不似錦 2019-08-17 21:44:05
代碼如下:constp=Promise.resolve();(()=>{constimplicit_promise=newPromise(resolve=>{constpromise=newPromise(res=>res(p));promise.then(()=>{console.log('after:await');resolve();});});returnimplicit_promise;})();p.then(()=>{console.log('tick:a');}).then(()=>{console.log('tick:b');}).then(()=>{console.log('tick:c');})??這段代碼在node11和瀏覽器中的輸出順序為:tick:atick:bafter:awaittick:c不應該先輸出after:await么?
查看完整描述

2 回答

?
qq_花開花謝_0

TA貢獻1835條經驗 獲得超7個贊

constp=Promise.resolve();
(()=>{
constimplicit_promise=newPromise(resolve=>{
//SYNC1
constsync1_promise=newPromise(res=>res(p)/*ASYNC2*/);
sync1_promise.then(()=>{
/*ASYNC3*/
console.log('after:await');
resolve();
});
});
returnimplicit_promise;
})();
p.then(()=>{
//TICKA
console.log('tick:a');
}).then(()=>{
//TICKB
console.log('tick:b');
}).then(()=>{
//TICKC
console.log('tick:c');
})
幾點注意:
Promise的then函數回調不會同步執行,如果Promise已經被resolve或reject,那么其回調會被放進異步隊列。當Promise并沒有被resolve或reject的時候,then的回調不會被放入任務隊列,而是在Promise在被resolve或reject的時候才放入異步隊列。
Promise的then(onFullfilled,onReject)會返回一個新的Promise,這個新的Promise會在onFullfilled或onReject別執行之后,被resolve或reject。
當使用Promise來rosolve另一個Promise的時候(res=>res(p)),會建立一個異步任務,并在異步任務里調用p.then(res)。
所以:同步任務,p是一個已經resolve的Promise。匿名函數直接調用,SYNC1執行,ASYNC2執行。ASYNC2執行并沒有resolvesync1_promise(見以上第三點),而是增加了一個異步任務(異步1),在異步任務里將執行p.then(res)。于是,SYNC1中的sync1_promise并沒有被resolve,ASYNC3也并不會被放入異步隊列。接下來,由于p已經resolve,TICKA被放入異步隊列(異步2)。但是,其返回Promise由于TICKA并沒有被調用(還在異步隊列里),并沒有被resolve,于是TICKB與TICKC均不會被放入異步隊列。
異步1:執行p.then(res),p已經resolve,所以res被放入異步隊列(異步3)異步2:執行TICKA,輸出"tick:a"。同時,rosolvep.then(TICKA)返回的Promise,TICKB被放入隊列(異步4)異步3:執行res(),resolve掉SYNC1中的sync1_promise,于是在它的then里注冊的ASYNC3被放入隊列(異步5)異步4:執行TICKB,輸出"tick:b"。同時,rosolvep.then(TICKA).then(TICKB)返回的Promise,TICKC被放入隊列(異步6)異步5:執行ASYNC3,輸出"after:await"。resolveimplicit_promise。異步6:執行TICKC,輸出"tick:c"
                            
查看完整回答
反對 回復 2019-08-17
?
素胚勾勒不出你

TA貢獻1827條經驗 獲得超9個贊

js是單線程,而promise是異步的,總是后執行,異步里套異步,也是先把同層級的異步任務跑完再去跑下一層級異步任務。造成這個的原因可以看下eventLoop;
這是別人的例子,可以看看想想。
setTimeout(function(){
console.log(1);
setTimeout(function(){
console.log(2);
},0);
},0);
setTimeout(function(){
console.log(3);
setTimeout(function(){
console.log(4);
},0);
},0);
結果打印1324,而不是1234。
鏈接描述JavaScript運行機制詳解:再談EventLoop
                            
查看完整回答
反對 回復 2019-08-17
  • 2 回答
  • 0 關注
  • 383 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號