js中A函数调用B函数,使用async/await的区别
背景,需要发起一个网络请求(setTimeout模拟),3秒得到结果。
要求必须在这个网路请求之后才能访问请求到的数据myRes。
要求调用方f4() 和 发起网络请求的f3()都必须用async/await。
假如f4()不用async/await,f3()用。代码执行到promise内部,执行完setTimeout加到宏任务-->输出“promise1000”,再遇见then加入到微任务。此时就跳出了await外部对应的async函数,继续执行同步代码"console.log(myRes+1);",这个时候myRes还没有有从网络获取到值“999”。
promise 3000 1 setTimeout 3000ms result 999 f3 最后一行
假如f4()用,f3()不用。
promise 3000 f3 最后一行 1 setTimeout 3000ms result 999
这两种情况在访问myRes的数值的时候“console.log(myRes+1);”,都还是原来的值“1”。
let myRes = 0;
async function f3() {// 模拟网络请求 console.log("f3"); let t=3000; await new Promise((res,rej)=>{ setTimeout(()=>{ console.log(`setTimeout ${t}ms`); res(999); } , t); console.log(`promise ${t}`); } ).then((result)=>{ myRes = result; console.log(`result ${result}`); } ); console.log("f3 最后一行") }; async function f4() { await f3(); console.log(myRes+1) } f4() // then后面部分需要等到前面promise执行完毕,才会加到queue // 在f4()中await后面紧跟的函数f3(),如果该函数f3()内部有promise: // 如果在f4()中,f4()想要f3()内部的promise和`console.log("f3 最后一行")`都执行结束过后,才执行await f3()的下一步" console.log(myRes+1)",那么f3()内的promise之前需要用await // 这种需求,f4()和f3()都需要用async/await
结果
f3 promise 3000 setTimeout 3000ms result 999 f3 最后一行 1000
1. tt()采用async/await,f()采用async/await.
会等到f()完全执行结束,才会输出“ffffffff”
console.log("code begin");
async function f() {
console.log("f")
await new Promise((res, rej) => {
let t = 1000;
setTimeout(() => {
console.log(`setTimeout ${t}ms`);
res(777);
}
, t);
console.log(`promise ${t}`);
})
.then((result) => {
console.log(`result ${result}`)
}
);
console.log("f-2")
}
async function tt() {
await f()
console.log("ffffffff")
}
console.log("f1")
tt();
console.log("code end");
// 1、tt()采用async/await,f()采用async/await.
// 会等到f()完全执行结束,才会输出“ffffffff”
// async function tt() {
// await f()
// console.log("fffffffff")
// }
/**
f1
f
promise 1000
code end
setTimeout 1000ms
result 777
f-2
ffffffff */
2. tt()不用(×)async/await,f()采用async/await。
tt()此时是同步代码,“ffffffff”会先于“code end”输出console.log("code begin");
async function f() {
console.log("f")
await new Promise((res, rej) => {
let t = 1000;
setTimeout(() => {
console.log(`setTimeout ${t}ms`);
res(777);
}
, t);
console.log(`promise ${t}`);
})
.then((result) => {
console.log(`result ${result}`)
}
);
console.log("f-2")
}
async function tt() {
f()
console.log("ffffffff")
}
console.log("f1")
tt();
console.log("code end");
// 2、tt()不用(×)async/await,f()采用async/await。
// tt()此时是同步代码,“ffffffff”会先于“code end”输出
// async function tt() {
// f()
// console.log("ffffffff")
// }
/**
f1
f
promise 1000
ffffffff
code end
setTimeout 1000ms
result 777
f-2 */
3. tt()采用async/await,f()不采用(×)async/await.
console.log("code begin");
async function f() {
console.log("f")
new Promise((res, rej) => {
let t = 1000;
setTimeout(() => {
console.log(`setTimeout ${t}ms`);
res(777);
}
, t);
console.log(`promise ${t}`);
})
.then((result) => {
console.log(`result ${result}`)
}
);
console.log("f-2")
}
async function tt() {
await f()
console.log("ffffffff")
}
console.log("f1")
tt();
console.log("code end");
// 3、tt()采用async/await,f()不采用(×)async/await.
// 正确
// code begin
// f1
// f
// promise 1000
// f-2
// code end
//因为Promise中用了setTimeout,“code end”输出后,不会执行setTimeout(宏任务)中的console,所以也不执行then(微任务)。
// (因为then必须等到Promise中所有内容执行完毕,setTimeout在Promise内部,所以then必须等到setTimeout执行完毕);
// 那tt()采用了async/await(awwit f()),为什么不等到f()执行完毕呢?
// 答:因为f()内部没有像第一点那样采用await Promise,其实f()已经执行完了,你看“f-2”都已经输出了。
// 如果Promise中没用用setTimeout,那么输出的情况将会是下面标记为【去掉setTimeout】的结果。
// ffffffff
// setTimeout 1000ms
// result 777
console.log("code begin");
async function f() {
console.log("f")
new Promise((res, rej) => {
let t = 1000;
// setTimeout(() => {
// console.log(`setTimeout ${t}ms`);
res(777);
// }
// , t);
console.log(`promise ${t}`);
})
.then((result) => {
console.log(`result ${result}`)
}
);
console.log("f-2")
}
async function tt() {
await f()
console.log("ffffffff")
}
console.log("f1")
tt();
console.log("code end");
// 【去掉setTimeout】
// code begin
// f1
// f
// promise 1000
// f-2
// code end
// result 777
// ffffffff
4. tt()不采用(×)async/await,f()不采用(×)async/await.
console.log("code begin");
async function f() {
console.log("f")
new Promise((res, rej) => {
let t = 1000;
setTimeout(() => {
console.log(`setTimeout ${t}ms`);
res(777);
}
, t);
console.log(`promise ${t}`);
})
.then((result) => {
console.log(`result ${result}`)
}
);
console.log("f-2")
}
async function tt() {
f()
console.log("ffffffff")
}
console.log("f1")
tt();
console.log("code end");
// 4、tt()不采用(×)async/await,f()不采用(×)async/await.
// code begin
// f1
// f
// promise 1000
// f-2
// ffffffff
// code end
// setTimeout 1000ms
// result 777
// 注释掉setTimeout
console.log("code begin");
async function f() {
console.log("f")
new Promise((res, rej) => {
let t = 1000;
// setTimeout(() => {
// console.log(`setTimeout ${t}ms`);
res(777);
// }
// , t);
console.log(`promise ${t}`);
})
.then((result) => {
console.log(`result ${result}`)
}
);
console.log("f-2")
}
async function tt() {
f()
console.log("ffffffff")
}
console.log("f1")
tt();
console.log("code end");
// code begin
// f1
// f
// promise 1000
// f-2
// ffffffff
// code end
// result 777
/**function f1() { asyncFunc() } async function f2() { await asyncFunc() } await f1() // 不会等待asyncFunc(),如果asyncFunc()返回rejection,直接触发 unhandledrejection await f2() // 会等待asyncFunc(),如果asyncFunc()返回rejection,会转回成错误并向上传播 链接:https://www.zhihu.com/question/462421951/answer/1916281835 */