Javascript 不正确的承诺返回值
我试图让一个函数返回一个id是否为有效id。 然而,事实证明,有时,即使Javascript 不正确的承诺返回值,javascript,promise,Javascript,Promise,我试图让一个函数返回一个id是否为有效id。 然而,事实证明,有时,即使wait isValidId(230)是true,validId也不是230 我认为这是因为承诺总是异步解决的。是这样吗?那么我该如何设计这个功能呢 let validId = 230; let isValidId = function(id){ return new Promise(resolve => { //async code resolve(validId === id); }); }
wait isValidId(230)
是true
,validId
也不是230
我认为这是因为承诺总是异步解决的。是这样吗?那么我该如何设计这个功能呢
let validId = 230;
let isValidId = function(id){
return new Promise(resolve => {
//async code
resolve(validId === id);
});
}
if (await isValidId(230)){
//validId is not necessary 230
}
这里有一个更完整的例子
let playerAskedToLogOut = false;
let playersOnline = ['MyUsername'];
let canPlayerUseItem = async function(player,itemId){
let hasItem = await Database.playerHasItem(player, itemId);
let isStillOnline = playersOnline.includes(player);
playerAskedToLogOut = true; //normally called by another function
return hasItem && isStillOnline;
};
setInterval(() => {
useItems();
logOutPlayers();
}, 100);
let useItems = async function(){
if (await canPlayerUseItem('MyUsername', 'hammer')){
//the player is not online anymore. Yet, await canPlayerUseItem returned true
}
}
let logOutPlayers = function(){
if(playerAskedToLogOut)
playersOnline = []
}
问题中的代码有一个语法错误:它在非async
函数中使用await
,该函数不起作用。(您已再次编辑代码以使canplayerSeItem
async
)
第一:在async
函数中使用newpromise
毫无意义。该函数自动为您创建承诺。因此,代码(在撰写本文时,您一直在更改它)实际上应该是:
let canPlayerUseItem = async function(player,itemId){
let hasItem = await Database.playerHasItem(player, itemId);
let isStillOnline = playersOnline.includes(player);
return hasItem && isStillOnline;
};
canplayerseitem
的承诺将以true
解决的唯一原因是hasItem
返回truthy并且playersOnline
包含player
在我们等待playershitem
之后的检查。。如果在您调用canPlayerUserItem
时播放机未联机,但在playerHasiItem
检查完成时播放机联机,则将使用true
进行解析
如果要在等待playerHasItem
之前执行playerOnline
检查,请呼叫:
let canPlayerUseItem = async function(player,itemId){
if (playersOnline.includes(player)) {
return false;
}
return await Database.playerHasItem(player, itemId);
};
或者,如果您想同时检查两个(但它们可能已脱机,然后在两者之间重新联机):
在您最近的编辑中,您建议在承诺解析之后将播放器从在线阵列中删除。这向我表明,您正在询问如何使用
canplayerseitem
在代码中知道播放器仍然在线
回答:你不能您在canplayerseitem
中所做的任何事情都不能保护您免受以下情况固有的竞争条件的影响:
if (await canPlayerUseItem(player, itemId)) {
// They player may now be offline
}
…因为玩家可以在CanPlayerSeItem
完成检查后,但在您的代码运行之前注销该结果。这就是异步代码的本质。以上基本上是这样的:
flag=canplayerseitem(玩家,项目ID)
if(flag).
(此时播放机可能不再登录)if (await Database.playerHasItem(player, itemId) && playersOnline.includes(player)) {
// As of this event loop, the player is online, and had the item
// when we checked a moment ago
}
即:
flag=Database.playerHasItem(player,itemId)
if(flag&&playersOnline.includes(player)
async
函数中使用await
,该函数不起作用。(您已再次编辑代码,使canplayerseitem
async
)
第一:在异步
函数中使用新承诺
毫无意义。该函数会自动为您创建承诺。因此,代码(在撰写本文时,您一直在更改它)实际上应该是:
let canPlayerUseItem = async function(player,itemId){
let hasItem = await Database.playerHasItem(player, itemId);
let isStillOnline = playersOnline.includes(player);
return hasItem && isStillOnline;
};
canplayerseitem
的承诺将以true
解决的唯一原因是hasItem
返回truthy并且playersOnline
包含player
我们执行该检查时,即我们等待playershitem
之后的之后。如果玩家在u调用canPlayerUserItem
,但当playerHitem
检查完成后,它将以true
进行解析
如果要在等待playerHasItem
之前执行playerOnline
检查,请呼叫:
let canPlayerUseItem = async function(player,itemId){
if (playersOnline.includes(player)) {
return false;
}
return await Database.playerHasItem(player, itemId);
};
或者,如果您想同时检查两个(但它们可能已脱机,然后在两者之间重新联机):
在您最近的编辑中,您建议在承诺解析之后从联机阵列中删除播放机。这向我表明,您正在询问如何使用
canplayerseitem
在代码中知道播放机仍然联机
回答:你不能。你在canplayerseitem
中所做的任何事情都不能保护你免受以下固有的种族状况的影响:
if (await canPlayerUseItem(player, itemId)) {
// They player may now be offline
}
…因为玩家可以在CanPlayerSeItem
完成检查后,但在您的代码使用结果运行之前注销。这是异步代码的本质。上面基本上是这样的:
flag=canplayerseitem(玩家,项目ID)
if(flag).
(此时播放机可能不再登录)if (await Database.playerHasItem(player, itemId) && playersOnline.includes(player)) {
// As of this event loop, the player is online, and had the item
// when we checked a moment ago
}
即:
flag=Database.playerHasItem(player,itemId)
if(flag&&playersOnline.includes(player)
为什么
isValidId
是异步的?分别:它真正的目的是什么?我想你必须向我们展示你的真实代码,包括异步代码,因为问题可能不在你在这里展示的代码中。什么是//异步代码
?为什么isValidId
是异步的?分别:它真正的目的是什么?我想你会我必须向我们展示你的真实代码,包括异步代码,因为问题可能不在你在这里展示的代码中。什么是//异步代码
?@RainingChain-问题的更新并不会真正改变答案:如果hasItem
是真实的,并且玩家仍然在线,它将用true
解决(例如,仍在PlayerOnline
阵列中)自