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

JavaScript忍者吃豆人游戏:水平移动无法累计多个寿司分数

问题分析与修复

你的问题出在移动后的寿司判断位置完全错位啦!咱们拆解一下问题根源,再给出修复方案:

错误到底在哪?

拿左移动的逻辑举例子:

  1. 你先检查 world[ninjaman.y][ninjaman.x - 1] != 1(确认要移动到的位置不是墙),这步没问题
  2. 然后执行 ninjaman.x--,忍者已经移动到新位置了
  3. 但你接下来判断的是 world[ninjaman.y][ninjaman.x - 1] == 2 —— 这时候ninjaman.x已经减过1了,等于你在检查忍者当前位置左边的第二个格子,根本不是刚刚移动到的那个寿司格子!

上下移动时你也犯了同样的错误,只是可能你的测试场景刚好蒙混过关(比如移动后的下一个格子碰巧也是寿司),但逻辑本身是完全错误的。

正确的逻辑流程

每个方向的操作都应该遵循这个顺序:

  1. 先算出忍者要移动到的目标位置
  2. 检查目标位置是不是墙,是墙就不移动
  3. 如果不是墙,先看目标位置是不是寿司,是就加分
  4. 把忍者移动到目标位置
  5. 把目标位置改成空白(表示寿司被吃掉,不会重复计分)
  6. 重新绘制游戏界面

修复后的代码

把你的document.onkeydown函数替换成下面的版本:

document.onkeydown = function(e) {
  let targetX = ninjaman.x;
  let targetY = ninjaman.y;

  // 先确定目标位置
  if (e.keyCode == 40) { // 向下
    targetY = ninjaman.y + 1;
  } else if (e.keyCode == 38) { // 向上
    targetY = ninjaman.y - 1;
  } else if (e.keyCode == 37) { // 向左
    targetX = ninjaman.x - 1;
  } else if (e.keyCode == 39) { // 向右
    targetX = ninjaman.x + 1;
  }

  // 检查目标位置是否可移动(不是墙)
  if (world[targetY][targetX] != 1) {
    // 吃到寿司就加分
    if (world[targetY][targetX] == 2) {
      ninjaScore += 1;
      console.log(`当前分数:${ninjaScore}`); // 可选:加日志方便看分数变化
    }
    // 移动忍者到目标位置
    ninjaman.x = targetX;
    ninjaman.y = targetY;
    // 把目标位置设为空白(吃掉寿司或覆盖位置)
    world[ninjaman.y][ninjaman.x] = 0;
    // 重新绘制游戏
    drawWorld();
    drawNinjaMan();
  }
}

为什么这样改?

  • 先统一计算目标位置,避免重复写相同逻辑,代码更清晰
  • 直接检查目标位置的寿司状态,这才是忍者真正要吃到的寿司,不会再出现位置错位
  • 移动后把目标位置设为0,确保同一个寿司不会被重复计分

这样修改后,不管上下还是左右移动,只要忍者吃到寿司,分数都会正确累计啦!

内容的提问来源于stack exchange,提问作者Amanda Demetrio

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.29 07:00:52