####前端似乎对 Promise 不满

优点

Async/Await替代Promise的6个理由

但是,除了更简洁意外,其他理由似乎都不是很有说服力。

为什么需要 async ?

看起来非常多余,await 所在的函数就是 async ,不是吗?

已经搜索发现,在 await 之前,已经有人实现了 await 函数,她的函数是这样的:

1
2
3
function fn () {
const result = await(xxx())
}

所以如果 JS 一发布这个语法,那么这个人就不能继续运行她的代码了,所以为了避免这种情况,JS 只能强行加一个 async 关键词(虽然没有任何实质意义)作区分(用心良苦,为了兼容旧代码里普通函数的await),继而保证大家都能使用。

如何优雅的处理错误

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
const ajax = function () {
return new Promise((resolve, reject) => {
setTimeout(() => {
reject({ status: 403, message: '无权限' })
}, 2000)
})
}

const errHandler = err => {
console.log(err)
throw err
}

async function fn () {
const res = await ajax().catch(errHandler)
console.log('继续运行接下来的代码')
}
fn()

上述的 errHandler 之所以最后 throw err 是因为,如果直接 return 一个值,会被直接赋值给 res,所以直接使用 throw err 还能打断程序进程,防止下面的代码继续运行。

缺点

具有传染性
1
2
3
console.log(1)
await console.log(2)
console.log(3)

console.log(3) 变成异步任务了,
Promise 同样具有传染性,then 里面都是异步,除非直接写在 下面。
谁没有传染性:回调。

天生串行
1
2
3
4
await ajax1()
await ajax2()
await ajax3()
await ajax4()

其中有一个陷阱关于循环的陷阱

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
const ajax1 = () => new Promise(resolve => {
setTimeout(() => {
console.log('ajax1')
resolve()
}, 2000)
})
const ajax2 = () => new Promise(resolve => {
setTimeout(() => {
console.log('ajax2')
resolve()
}, 2000)
})
const ajax3 = () => new Promise(resolve => {
setTimeout(() => {
console.log('ajax3')
resolve()
}, 2000)
})
const fn = async () => {
const array = [ajax1, ajax2, ajax3];
for (let i = 0; i < array.length; i++) {
await array[i]()
}
}
fn()

用普通的 for 循环是正常的

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
const ajax1 = () => new Promise(resolve => {
setTimeout(() => {
console.log('ajax1')
resolve()
}, 2000)
})
const ajax2 = () => new Promise(resolve => {
setTimeout(() => {
console.log('ajax2')
resolve()
}, 2000)
})
const ajax3 = () => new Promise(resolve => {
setTimeout(() => {
console.log('ajax3')
resolve()
}, 2000)
})

const fn2 = async () => {
const array = [ajax1, ajax2, ajax3];
array.map(async ajax => await ajax())
}
fn2()

当用 map 遍历的时候,就会同时运行三个 ajax