You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

TypeScript中whoWins函数返回值报错:如何正确返回指定类型值

TypeScript函数返回值错误修复:forEach回调return不生效问题

问题说明

编写whoWins()函数时声明了返回类型为{ player1Score: number; player2Score: number; message: string },但TypeScript报错:"A function whose declared type is neither 'void' nor 'any' must return a value"。核心原因是仅在forEach循环的回调函数内执行return,外层函数未返回任何值,导致TS推断函数为void类型,与声明的返回类型冲突。

解决思路

forEach的回调里的return只会终止当前回调迭代,无法将值返回给外层的whoWins函数。需要改用能中断循环并返回值的方法,比如find方法、for...of循环,或者手动遍历并在外层返回结果。

方案1:使用find定位匹配规则后返回结果

find会遍历数组,找到第一个符合条件的元素后停止遍历,基于找到的规则直接生成返回对象即可。

方案2:使用for...of循环遍历规则集

直接在外层循环中处理逻辑,找到匹配项后立即return结果,既能终止循环,又能将值返回给外层函数。

修正后的代码示例

方案1(基于find实现)

whoWins(
  player1Choice: string,
  player2Choice: string
): { player1Score: number; player2Score: number; message: string } {
  // 找到player1选择对应的规则
  const matchedRule = ruleSet.find(rule => rule.choice === player1Choice);
  
  // 处理未找到规则的边界情况(根据业务需求调整)
  if (!matchedRule) {
    return {
      player1Score: this._player1Score,
      player2Score: this._player2Score,
      message: 'Invalid choice'
    };
  }

  if (matchedRule.losesTo.includes(player2Choice)) {
    return {
      player1Score: this._player1Score,
      player2Score: ++this._player2Score,
      message: 'player2 Wins',
    };
  } else if (matchedRule.beats.includes(player2Choice)) {
    return {
      player1Score: ++this._player1Score,
      player2Score: this._player2Score,
      message: 'player1 Wins',
    };
  } else {
    return {
      player1Score: this._player1Score,
      player2Score: this._player2Score,
      message: 'Draw',
    };
  }
}

方案2(基于for...of实现)

whoWins(
  player1Choice: string,
  player2Choice: string
): { player1Score: number; player2Score: number; message: string } {
  for (const rule of ruleSet) {
    if (rule.choice === player1Choice) {
      if (rule.losesTo.includes(player2Choice)) {
        return {
          player1Score: this._player1Score,
          player2Score: ++this._player2Score,
          message: 'player2 Wins',
        };
      } else if (rule.beats.includes(player2Choice)) {
        return {
          player1Score: ++this._player1Score,
          player2Score: this._player2Score,
          message: 'player1 Wins',
        };
      } else {
        return {
          player1Score: this._player1Score,
          player2Score: this._player2Score,
          message: 'Draw',
        };
      }
    }
  }

  // 必须处理未找到匹配规则的情况,保证所有代码路径都有返回值
  return {
    player1Score: this._player1Score,
    player2Score: this._player2Score,
    message: 'Invalid choice'
  };
}

额外注意事项

  • 必须处理未找到匹配规则的边界情况,否则TS仍会报错(因为存在无返回值的代码路径)。
  • forEach的设计目的是遍历执行副作用,不适合用于需要返回结果的场景,避免在这类场景中使用它。

内容的提问来源于stack exchange,提问作者Exodus Reed

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.31 13:15:24