异步函数返回一个承诺数组而不是实际的值数组

我有一个函数,它将接受一个整数数组,然后它将调用另一个函数,该函数将接受一个整数并进行一些检查并返回一个承诺来解决它。


我知道 getDataById 函数并不依赖于做异步工作,但在我看来这只是例子..


这是我的代码:


function getDataById(id) {

    return new Promise((resolve, reject) => {

        if (id > 0) resolve(id * 10);

        if (id <= 0) reject("wrong input");

    })

}


async function callService(idList) {

    return await idList.map((id) => getDataById(id));

}


let teamIDList = [1, 2, 3, 4, 5, 6, 7, 8, 9, 0, -1, -2, -3, -4];



callService(teamIDList).then(res => {

    console.log(res);

});

我希望它会返回一个新数字数组和一些字符串。但它返回了一系列承诺。


临摹微笑
浏览 132回答 1
1回答

慕少森

await 当你给它一个数组时并没有做任何特别的事情,它只是将数组包装在一个已解决的承诺中。要等待承诺解决,请使用Promise.all:async function callService(idList) {&nbsp; &nbsp; return await Promise.all(idList.map((id) => getDataById(id)));}交替:function callService(idList) {&nbsp; &nbsp; return Promise.all(idList.map((id) => getDataById(id)));}(旁注:不需要那个箭头函数:return await Promise.all(idList.map(getDataById));)请注意,它们都按以下顺序执行操作:getDataById为每个调用id等待所有这些承诺都实现,或者其中一个失败如果它们都实现了,则使用结果数组来解析callService的承诺(记住,async函数总是返回承诺)如果您想getDataById在对 进行下一次调用之前等待每个调用完成getDataById,您可以使用一个简单的循环来完成:// **IF** you wanted to wait for each `getDataById` call to finish// before starting the nextasync function callService(idList) {&nbsp; &nbsp; const result = [];&nbsp; &nbsp; for (const id of idList) {&nbsp; &nbsp; &nbsp; &nbsp; result.push(await getDataById(id));&nbsp; &nbsp; }&nbsp; &nbsp; return result;}(reduce如果你愿意,你也可以把它硬塞进去,但它不会给你买任何东西。)但我认为你想要上面的第一个代码块,并行启动所有调用并等待它们完成。你在评论中说你的老板不希望你使用,Promise.all因为如果任何承诺拒绝,它就会拒绝。确实如此,确实如此。如果你不想那样,你可能想allSettled改用。这是第 4 阶段的提案(例如,在 JavaScript 引擎中积极实施),它很容易被 polyfill。async function callService(idList) {&nbsp; &nbsp; return await Promise.allSettled(idList.map(getDataById));}交替:function callService(idList) {&nbsp; &nbsp; return Promise.allSettled(idList.map(getDataById));}结果是一个对象数组,其中已履行的承诺如下所示:{&nbsp; &nbsp; status: "fulfilled",&nbsp; &nbsp; value: (the value)}被拒绝的看起来像这样:{&nbsp; &nbsp; status: "fulfilled",&nbsp; &nbsp; reason: (the rejection reason)}显然,如果你想转换那个数组,你可以很容易地做到这一点。例如,如果您想返回null无法检索的那些:async function callService(idList) {&nbsp; &nbsp; return (await Promise.allSettled(idList.map(getDataById)))&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;.map(entry => entry.status === "fulfilled" ? entry.value : null);}或者,如果您想过滤掉它们:async function callService(idList) {&nbsp; &nbsp; return (await Promise.allSettled(idList.map(getDataById)))&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;.map(entry => entry.status === "fulfilled" ? entry.value : null)&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;.filter(entry => entry !== null);}如果你想同时过滤和映射,我们可以稍微滥用flatMap:-)async function callService(idList) {&nbsp; &nbsp; return (await Promise.allSettled(idList.map(getDataById)))&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;.flatMap(entry => entry.status === "fulfilled" ? entry.value : []);}
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

JavaScript