Empresas
Empregos
  • Sobre nós
  • Soluções
    • Publicação de vagas
      Publique sua vaga e receba candidatos qualificados em 48h.
    • Avaliações de candidatos
      Mais de 500 testes técnicos e psicológicos, mais anti-fraude.
    • Headhunting
      Busca executiva personalizada do início ao fim.
    • Folha de Pagamento + EOR
      Dispersão de folha e EOR em mais de 15 países da LATAM.
  • Preços
  • Empregos

0

116
Visualizações
Can't get backtrack to work on recursive javascript sudoku sovler

I'm racking my brain but I can't see where I've gone wrong, from the console log it appears it's an issue when it comes to backtracking not working correctly, I think it has something to do with how I'm working with position object, any help would be appreciated,

It works up until the backtracking is supposed to work, and I can see it does infact backtrack 6 times, but the position doesn't actually go back and alter the previous numbers

let grid = [];

const solve = function (pos) {
  while (pos.x < 9 && pos.y < 9 && grid[pos.x][pos.y].value) {
    pos = incrementPos(pos);
  } // skip non-empty cells
  if (pos.y == 9) return true;

  for (let m = 1; m < 10; m++) {
    grid[pos.x][pos.y].value = m;
    console.log(pos, m);
    if (isValid(m, pos)) {
      if (solve(incrementPos(pos))) {
        return true;
      }
    }
  }
  console.log("start backtrack", pos);
  grid[pos.x][pos.y].value = "";
  return false;
};

function isValid(n, pos) {
  let valid = true;
  let row = checkRow(n, pos);
  let col = checkCol(n, pos);
  let block = checkBlock(n, pos);
  if (!row || !col || !block) {
    return false;
  } else {
    return true;
  }
}

function checkBlock(n, pos) {
  let startX = parseInt(pos.x / 3) * 3;
  let startY = parseInt(pos.y / 3) * 3;

  for (let x = startX; x < startX + 3; x++) {
    for (let y = startY; y < startY + 3; y++) {
      if ((grid[x][y].value === n) & (x !== pos.x) & (y !== pos.y)) {
        return false;
      }
    }
  }
  return true;
}

function checkRow(n, pos) {
  for (let t = 0; t < 9; t++) {
    if (grid[t][pos.y].value === n && t !== pos.x) {
      return false;
    }
  }
  return true;
}

function checkCol(n, pos) {
  for (let t = 0; t < 9; t++) {
    if ((grid[pos.x][t].value === n) & (t !== pos.y)) {
      return false;
    }
  }
  return true;
}

function incrementPos(pos) {
  if (pos.x < 8) {
    pos.x++;
  } else {
    pos.y++;
    pos.x = 0;
  }

  return pos;
}

const initGrid = function () {
  for (let x = 0; x < 9; x++) {
    let col = [];

    for (let y = 0; y < 9; y++) {
      let el = {};
      el.locked = false;
      el.value = "";
      el.location = document.querySelector("#r" + (y + 1) + "c" + (x + 1));
      col.push(el);
    }

    grid.push(col);
  }
  displayGrid();
};

const displayGrid = function () {
  for (let x = 1; x < 10; x++) {
    for (let y = 1; y < 10; y++) {
      document.querySelector("#r" + y + "c" + x).textContent =
        grid[x - 1][y - 1].value;
    }
  }
};
about 4 years ago · Juan Pablo Isaza
1 Respostas
Responde à pergunta

0

I can't really figure out what you're doing, it's too much, however I can't see where you're actually resetting the position. I'm looking for something like this:

const getBlock = (block) => {
  if (block === 9) {
    return true
  }
  // you can use a total variable here to try it a couple of times before backtracking
  const valid = false

  ...

  if (valid) {
    getBlock(++block)
  } else {
    getBlock(--block)
  }
}

That code isn't perfect at all but it's just to show you the idea, you should be increasing the block if it's valid and after a couple of iterations where you can't find another block after that you should reset the block back to the previous one and try again. The result with backtracking is that if you console log the blocks you should see something like: 1 -> 2 -> 3 -> 4 -> 3 -> 4 -> 5 -> 4 -> 3 -> 4 -> 5 -> 6 -> ... on and on back and forth until you eventually find a solution.

In your own code I'd expect it to be something like:

if (solve(incrementPos(pos))) {          
  return true
} else {
  solve(decrementPos(pos)) // or something
  // otherwise you're not actually backtracking
}

Side note, you can use modular arithmetic instead of loops. If you know that you're in a specific block then you can immediately validate/invalidate and check if the values exist in correlating rows/columns/diagonals without any loops. Just a tip.

about 4 years ago · Juan Pablo Isaza Relatório
Responde à pergunta
Encontrar trabalhos remotos

Descubra a nova forma de encontrar um emprego!

melhores empregos
Principais categorias de trabalho
Empresas
Postar vaga Preços Comercial
Jurídico
Termos e Condições Política de privacidade
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomende algumas ofertas para mim
Preciso de ajuda