打印所有可能的国际象棋骑士动作-JS

时间:2019-05-02 10:55:21

标签: javascript

我有一个带有国际象棋骑士位置输入值(例如D4)的表格。单击“显示”后,系统应显示从定义位置(例如C2 E2 F3 F5 E6 C6 B3 B5)的所有可能的移动(坐标)。

let form = document.getElementById("chessKnight")
let btn = document.getElementById("button")
btn.addEventListener("click", chessKnight)

function chessKnight(cell) {
  var possibleCoordinates = [];
  var xCoordinates = ['A', 'B', 'C', 'D', 'E', 'F', 'G', 'H'];
  var cellX = xCoordinates.indexOf(cell[0]) + 1;
  var cellY = parseInt(cell[1]);

  var cellXpositions = [cellX + 2, cellX - 2, cellX + 1, cellX -
    1
  ].filter(function(cellPosition) {
    return (cellPosition > 0 && cellPosition < 9);
  })

  var cellYpositions = [cellY + 2, cellY - 2, cellY + 1, cellY -
    1
  ].filter(function(cellPosition) {
    return (cellPosition > 0 && cellPosition < 9);
  })

  for (var i = 0; i < cellXpositions.length; i++) {
    for (var j = 0; j < cellYpositions.length; j++) {
      if (!possibleCoordinates.includes([cellXpositions[i],
          cellYpositions[j]
        ])) {
        possibleCoordinates.push([cellXpositions[i],
          cellYpositions[j]
        ]);
      }
    }
  }
  console.log('Possible Coordinates:', possibleCoordinates);
  return possibleCoordinates.length;
}
<input id="chessKnight" type="text">
<button id="button">Show</button>

系统显示以下内容:“可能的坐标:” []

2 个答案:

答案 0 :(得分:1)

您必须将cell传递给函数,否则脚本无法读取单元格的属性

// your button calls the function without passing the cell
chessKnight() 

// but the function expects a cell
function chessKnight(cell) {
   console.log(cell)
}

您可以通过阅读表格的值来修正它

HTML

<input id="chessKnight" type="text">
<button id="button">Show</button>    

JS

let form = document.getElementById("chessKnight")
let btn = document.getElementById("button")
btn.addEventListener("click", chessKnight)

function chessKnight() {
   var cell = form.value
   console.log(cell)
}

更新

我添加了一个从输入字段获取行和列的函数。使用fromCharCodecharCodeAt将字母转换为数字,反之亦然。

将行和列作为数字后,就可以进行计算了。计算完后,再次将数字转换回字母。

在此解决方案中,我有一系列可能的骑士动作(对于一个骑士来说,总是8个动作),但是您也可以使用数学函数来解决这个问题。

let form = document.getElementById("chessKnight")
let knightBtn = document.getElementById("button")
let result = document.getElementById("result")
knightBtn.addEventListener("click", showPossibleMoves)


function showPossibleMoves() {
  let cell = form.value
  // convert letter to number
  let x = parseInt(cell.substring(0,1).charCodeAt() - 64)
  let y = parseInt(cell.substring(1,2))
  
  let knightMoves = [
    {x:2, y:-1},{x:2, y:1},{x:1, y:-2},{x:1, y:2},
    {x:-2, y:-1},{x:-2, y:1},{x:-1, y:-2},{x:-1, y:2}
  ]
  
  let possibleMoves = []
  for(let m of knightMoves) {
    let row = String.fromCharCode(x + m.x + 64)
    let column = y+m.y
    possibleMoves.push(row + "" + column)
  }
  console.log('Possible Coordinates:', possibleMoves);
  result.innerHTML = possibleMoves.toString()
}
<input id="chessKnight" type="text" value="D4">
<button id="button">Knight Moves</button>
<div id="result"></div>

答案 1 :(得分:0)

您可以使用一个坐标系统,其中一个位置用一个整数表示:行3位,列3位,每位前加1位以检测上溢/下溢。因此位置是用8位编码的。

它允许输入短代码:

function chessKnight(pos) {
  pos = pos[1]-1 + ("ABCDEFGH".indexOf(pos[0].toUpperCase()) << 4); // Convert

  return [-0x12, -0x21, -0x1F, -0x0E, 0x12, 0x21, 0x1F, 0x0E] // All relative moves
      .map(i => pos+i) // Add to current position
      .filter(i => !(i & 0x88)) // Detect under/overflow, i.e. off-the-board
      .map(i => "ABCDEFGH"[i>>4] + ((i & 7)+1)); // Convert to output format
}

// I/O handling:
const knight = document.getElementById("chessKnight");
const btn = document.getElementById("button");
const output = document.getElementById("output");
btn.addEventListener("click", () => {
    const moves = chessKnight(knight.value);
    output.textContent = `${moves.length} possible moves: ${moves}`;
});
<input id="chessKnight" type="text">
<button id="button">Show</button>
<div id="output"></span>