【问题标题】:Where has my logic gone wrong in my attempt to implement a sudoku solver in Javascript?在尝试用 Javascript 实现数独求解器时,我的逻辑哪里出了问题?
【发布时间】:2020-08-26 02:16:38
【问题描述】:

const N = 4;
const fourbyfour = [
  [1, 0, 0, 4],
  [3, 4, 1, 2],
  [2, 1, 4, 3],
  [4, 3, 2, 1],
];

function solve(board) {
  for (let i = 0; i < N; i++) {
    for (let j = 0; j < N; j++) {
      if (board[i][j] === 0) {
        for (let k = 1; k < N + 1; k++) {
          board[i][j] = k;
          if (isValidBoard(board)) {
            if (isSolved(board)) return board;
            else solve(board);
          }
        }
      }
    }
  }
  return;
}

function isSolved(board) {
  let cells = [];
  for (let row of board) {
    cells.push(...row);
  }
  return !cells.includes(0);
}

function isValidBoard(board) {
  // Check rows are valid
  for (let i = 0; i < N; i++) {
    const row = board[i].filter((cell) => cell !== 0);
    if (new Set(row).size !== row.length) {
      return false;
    }
  }

  // Check columns are valid
  for (let i = 0; i < N; i++) {
    let column = [];
    for (let j = 0; j < N; j++) {
      if (board[j][i] !== 0) column.push(board[j][i]);
    }
    if (new Set(column).size !== column.length) {
      return false;
    }
  }

  const root = Math.sqrt(N);
  // Check each grid
  for (let i = 0; i < N; i += root) {
    for (let j = 0; j < N; j += root) {
      const square = [];
      for (let k = i; k < i + root; k++) {
        for (let l = j; l < j + root; l++) {
          if (board[k][l] !== 0) {
            square.push(board[k][l]);
          }
        }
      }
      if (new Set(square).size !== square.length) {
        return false;
      }
    }
  }
  return true;
}
console.table(solve(fourbyfour));

solve() 继续返回未定义。 我相当确定问题出在求解函数中,与 isSolved() 和 isValidBoard() 无关。解决函数正在获取正确的电路板,如果我控制台记录电路板而不是返回它,则会打印正确的电路板,但由于某种原因它没有被返回。

【问题讨论】:

  • 我觉得添加几个大括号可以帮助您解决问题。
  • 你不应该在这里返回值,即else solve(board);应该是else { return solve(board); }吗?
  • 谢谢!你是对的。 @user2740650

标签: javascript recursion backtracking sudoku recursive-backtracking


【解决方案1】:

您永远不会返回递归的值。您需要从输入solve次返回。

另外,console.table 不适合在 sn-p 中工作

const N = 4;
const fourbyfour = [
  [1, 0, 0, 4],
  [3, 4, 1, 2],
  [2, 1, 4, 3],
  [4, 3, 2, 1],
];

function solve(board) {
  for (let i = 0; i < N; i++) {
    for (let j = 0; j < N; j++) {
      if (board[i][j] === 0) {
        for (let k = 1; k < N + 1; k++) {
          board[i][j] = k;
          if (isValidBoard(board)) {
            if (isSolved(board)) {
              return board;
            } else {
              return solve(board);
            }
          }
        }
      }
    }
  }
  return 'test';
}

function isSolved(board) {
  let cells = [];
  for (let row of board) {
    cells.push(...row);
  }
  return !cells.includes(0);
}

function isValidBoard(board) {
  // Check rows are valid
  for (let i = 0; i < N; i++) {
    const row = board[i].filter((cell) => cell !== 0);
    if (new Set(row).size !== row.length) {
      return false;
    }
  }

  // Check columns are valid
  for (let i = 0; i < N; i++) {
    let column = [];
    for (let j = 0; j < N; j++) {
      if (board[j][i] !== 0) column.push(board[j][i]);
    }
    if (new Set(column).size !== column.length) {
      return false;
    }
  }

  const root = Math.sqrt(N);
  // Check each grid
  for (let i = 0; i < N; i += root) {
    for (let j = 0; j < N; j += root) {
      const square = [];
      for (let k = i; k < i + root; k++) {
        for (let l = j; l < j + root; l++) {
          if (board[k][l] !== 0) {
            square.push(board[k][l]);
          }
        }
      }
      if (new Set(square).size !== square.length) {
        return false;
      }
    }
  }
  return true;
}
console.log(solve(fourbyfour));

【讨论】:

    猜你喜欢
    • 2022-01-19
    • 1970-01-01
    • 1970-01-01
    • 2016-02-22
    • 1970-01-01
    • 2010-10-11
    • 1970-01-01
    • 1970-01-01
    • 2016-01-15
    相关资源
    最近更新 更多