LeetCode #37: Sudoku Solver — Solved in Java
Backtracking with Direct Checks and Backtracking with Bit Masks and Precomputed Empties
Sudoku Solver asks for a valid way to fill every empty cell on a nine by nine grid so the finished board respects row, column, and box limits. Each empty space holds a digit from one to nine, and the board arrives partly filled with fixed values that can’t be touched. The search must build a complete and valid grid, and the result should modify the input board directly.
Work on this problem tends to open with a step by step scan of the grid and a way to test guesses quickly. Java fits this well because arrays and char math keep the checks light, and recursion gives a natural structure for backing up from dead ends. Thinking about how to track used digits is the anchor here. Some paths favor direct scans of row, column, and box checks on every guess, while others keep faster bit markers for rows, columns, and boxes. Both fall under the same backtracking idea, but the data you keep on hand changes how quickly you can rule out a direction.
Write a program to solve a Sudoku puzzle by filling the empty cells.
A sudoku solution must satisfy all of the following rules:
Each of the digits
1-9must occur exactly once in each row.Each of the digits
1-9must occur exactly once in each column.Each of the digits
1-9must occur exactly once in each of the 93x3sub-boxes of the grid.The
‘.’character indicates empty cells.Example 1:
Input: board = [[”5”,”3”,”.”,”.”,”7”,”.”,”.”,”.”,”.”],[”6”,”.”,”.”,”1”,”9”,”5”,”.”,”.”,”.”],[”.”,”9”,”8”,”.”,”.”,”.”,”.”,”6”,”.”],[”8”,”.”,”.”,”.”,”6”,”.”,”.”,”.”,”3”],[”4”,”.”,”.”,”8”,”.”,”3”,”.”,”.”,”1”],[”7”,”.”,”.”,”.”,”2”,”.”,”.”,”.”,”6”],[”.”,”6”,”.”,”.”,”.”,”.”,”2”,”8”,”.”],[”.”,”.”,”.”,”4”,”1”,”9”,”.”,”.”,”5”],[”.”,”.”,”.”,”.”,”8”,”.”,”.”,”7”,”9”]] Output: [[”5”,”3”,”4”,”6”,”7”,”8”,”9”,”1”,”2”],[”6”,”7”,”2”,”1”,”9”,”5”,”3”,”4”,”8”],[”1”,”9”,”8”,”3”,”4”,”2”,”5”,”6”,”7”],[”8”,”5”,”9”,”7”,”6”,”1”,”4”,”2”,”3”],[”4”,”2”,”6”,”8”,”5”,”3”,”7”,”9”,”1”],[”7”,”1”,”3”,”9”,”2”,”4”,”8”,”5”,”6”],[”9”,”6”,”1”,”5”,”3”,”7”,”2”,”8”,”4”],[”2”,”8”,”7”,”4”,”1”,”9”,”6”,”3”,”5”],[”3”,”4”,”5”,”2”,”8”,”6”,”1”,”7”,”9”]] Explanation: The input board is shown above and the only valid solution is shown below:Constraints:
board.length == 9
board[i].length == 9
board[i][j]is a digit or‘.’.It is guaranteed that the input board has only one solution.
I usually include the full code as a screenshot to make it easier to read on phones since Substack’s code formatting can be tough to follow on smaller screens. Hard solutions tend to be much longer than usual though, so capturing everything in one image isn’t always practical. You can still copy and run the complete solutions below, and at the end of the article you’ll find the same full code again with even more added comments to help follow along.
Solution 1: Backtracking with Direct Checks
In this solution, we walk through the board cell by cell and try digits whenever it sees a dot. A helper method checks row, column, and box every time a digit is placed. When a choice leads to a dead end, recursion backs up, erases the digit, and tries the next one.
Keep reading with a 7-day free trial
Subscribe to Alexander Obregon's Substack to keep reading this post and get 7 days of free access to the full post archives.



