我正在开发一些Nodejs脚本,并且对JS本身中async关键字的用法有疑问。
例如,假设我有一个函数返回这样的承诺:
function myFunction () {
... some job
return new Promise(async (resolve, reject) => {
const innerResult = await someHeavyJob();
... some job
resolve(innerResultThatIsManipulated);
});
}
我可以用另一种方式写它:
async function myFunction () {
... some job
const innerResult = await someHeavyJob();
... some job
return innerResultThatIsManipulated;
}
但是我有一个问题,如果我选择第一个解决方案,那我可以使用async
关键字吗?是否建议这样做?例如,如下所示:
async function myFunction () {
... some job
return new Promise(async (resolve, reject) => {
const innerResult = await someHeavyJob();
... some job
resolve(innerResultThatIsManipulated);
});
}
要强调这是一个异步方法,并且会在其代码的所有路径中返回promise(不是简单的对象)。
那么,推荐的使用方式是什么?
答案 0 :(得分:1)
MDN说:
异步函数声明定义了一个异步函数-a 返回AsyncFunction对象的函数。异步功能 通过事件以与其余代码不同的顺序进行操作 循环中,返回一个隐含的承诺作为结果。但是语法和 使用异步功能的代码结构看起来像标准 同步功能。
这样做:
async function myFunction () {
return new Promise(async (resolve, reject) => {
const innerResult = await someHeavyJob();
resolve(innerResult);
});
}
您返回的是隐含的诺言,该诺言返回了诺言。您问过,让代码更具可读性是否会是一种有趣的方法,我相信它会使您混淆不清。
(甚至不谈论在async函数内部的promise中的异步函数,该函数实际上仅包含那个仅包含该async函数的promise,我谈论的第一个不是最后一个,我的意思是第二个,您遵循了吗?编辑:您实际上已经编辑了该代码段,仅用于示例)
MDN添加:
async / await的目的是简化同步使用Promise
在我的理解中,异步功能是对Promise的替代,而不是每个说法的扩展。因此,按照您的建议将两者结合起来似乎是不明智的。
答案 1 :(得分:1)
在所有显示的示例中,只有第二个是正确的。其背后的原因是Promise
是一个构造函数(因此您将其与new
一起使用)采用了常规函数,而不是另一个Promise
作为参数。
示例1
解释器将您的第一个示例翻译成(理论上)这样的内容:
new Promise( new Promise((resolve, reject) => { ... }))
这不是您想要的,也被认为是反模式。相反,您需要这样做:
new Promise((resolve, reject) => { ... })
此外,似乎您已经具有一个产生someHeavyJob
的函数(Promise
)。为什么要将它包装在另一个Promise
中?只需使用.then
返回的Promise
的{{1}}方法就可以转换给您的内容。
最后,您会得到类似的东西:
someHeavyJob
示例3
出于相同的原因,从技术和逻辑角度讲,第三个示例都不正确,第三个示例不正确。
一般经验法则
请勿将function myFunction() {
// ... some job
return someHeavyJob().
then( result => {
// ... some job with result
})
}
和async
(仅)用作传达某些功能本质上与其他人(或您将来的自己)异步的方式。这两个关键字都会对您编写的代码产生隐式影响,并使其行为有所不同。
尝试同时遵守这两种约定(使用await
/ Promise
使用async
或)。仅在确实需要时将它们混合。
我个人而言,我尝试坚持使用await
而不是Promise
/ async
,因为它们经常使人们感到烦恼,而且-对我来说-他们俩都没有带来太多好处除了使代码“看起来更好”。但是,那只是我个人的看法。