Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Promise 执行顺序 #42

Open
nmsn opened this issue Sep 6, 2022 · 6 comments
Open

Promise 执行顺序 #42

nmsn opened this issue Sep 6, 2022 · 6 comments

Comments

@nmsn
Copy link
Owner

nmsn commented Sep 6, 2022

Promise.resolve()
  .then(() => {
    console.log(0);
    return Promise.resolve(4);
  })
  .then((res) => {
    console.log(res);
  });

Promise.resolve()
  .then(() => {
    console.log(1);
  })
  .then(() => {
    console.log(2);
  })
  .then(() => {
    console.log(3);
  })
  .then(() => {
    console.log(5);
  })
  .then(() => {
    console.log(6);
  });

执行结果

0123456
@nmsn nmsn added the 面试题 label Sep 6, 2022
@nmsn
Copy link
Owner Author

nmsn commented May 16, 2023

Promise.resolve(1).then(2).then(Promise.resolve(3)).then(console.log)

执行结果

1

then 方法传入非函数会透传

@nmsn
Copy link
Owner Author

nmsn commented May 16, 2023

const promise = Promise.resolve().then(() => { return promise });

会报错

then/catch 不能返回 promise 本身,否则会造成死循环

@nmsn
Copy link
Owner Author

nmsn commented May 16, 2023

Promise.resolve(1)
  .then(res => { console.log(res) })
  .finally(() => console.log('finally'));

Promise.resolve(2)
  .finally(() => {
    console.log('finally2');
    return '我是 finally2 返回的数';
  })
  .then(res => {
    console.log('finally2 后面的 then 函数', res);
});

执行结果

1
finally2
finally
finally2 后面的 then 函数 2

特征

  1. finally 方法不管 Promise 对象最后的状态如何都会执行
  2. finally 方法的回调函数不接受任何的参数,也就是说你在 finally 函数中是无法知道 Promise 最终的状态是 resolved 还是 rejected
  3. finally 最终返回的默认会是上一次的 Promise(finally 中 return 数据不会记录到 Promise 当中),不过如果抛出的是一个异常则返回异常的 Promise 对象

@nmsn
Copy link
Owner Author

nmsn commented May 16, 2023

function runAsync(x) {
  const p = new Promise(r => setTimeout(() => r(x, console.log(x)), 1000));
  return p;
}

function runReject(x) {
  const p = new Promise((res, rej) => setTimeout(() => rej(`Error:${x}`, console.log(x)), 1000 * x));
  return p;
}

Promise.all([runAsync(1), runReject(4), runAsync(3), runReject(2)])
  .then(res => console.log(res))
  .catch(err => console.log(err));

执行结果

// 1s
1
3
// 2s
2
Error: 2
// 4s
4

特征

  1. Promise.all 无法中止异步事件的执行

@nmsn
Copy link
Owner Author

nmsn commented May 17, 2023

async function async1() {
    console.log('async start');
    await async2();
    console.log('async1 end');
    setTimeout(() => {
      console.log('timer1');  
  }, 0);
}

async function async2() {
  setTimeout(() => {
    console.log('timer2');
  }, 0);
  console.log('async2');
}

async1();
setTimeout(() => {
  console.log('timer3');
}, 0);

console.log('start');
}

执行结果

async1 start
async2
start
async1 end
timer2
timer3
timer1

特征

  1. await 阻塞执行,await 后面的语句相当于放入到 new Promise 中,下一行及之后的语句相当于放在 Promise.then 中,也就是说, await 后面的语句中的代码是会执行的,阻塞的是 return 语句

@nmsn
Copy link
Owner Author

nmsn commented May 17, 2023

const p1 = new Promise((resolve) => {
  setTimeout(() => {
    resolve('resolve3');
    console.log('timer1');
  }, 0);
  resolve('resolve1');
  resolve('resolve2');
}).then(res => {
  console.log(res);
  setTimeout(() => {
    console.log(p1);
  }, 1000);
}).finally(res => {
  console.log('finally', res);
})

执行结果

resolve1
finally undefiend
timer1
Promise{<resolved>: undefined}

特征

finally 的返回值如果在没有抛出错误的情况下默认会是上一个 Promise 的返回值,而这道题中的 finally 上一个 Promise 是 then,但是这个 then 并没有返回值,所以 跑
打印出来的 Promise 的值回事 undefined

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

1 participant