I've been trying to modify TechWithTim's Sudoku solver. I've got it so that it generates a random board, but I am not sure how to ensure that there will be just one unique solution to the puzzle. Any ideas on how I can implement this?
import random
n = 3
m = n**2
def make_board(bo):
possible_answers = [_ for _ in range(1, m+1)]
# print(possible_answers)
find = find_empty(bo)
if not find:
return True
else:
row, col = find
random.shuffle(possible_answers)
for i in possible_answers:
# i = random.randint(1, 9)
if valid(bo, i, (row, col)):
bo[row][col] = i
if make_board(bo):
return True
bo[row][col] = 0
return False
counter = 1
def solve(bo):
global counter
find = find_empty(bo)
if not find:
counter += 1
return True
else:
row, col = find
for i in range(1, m+1):
if valid(bo, i, (row, col)):
bo[row][col] = i
if solve(bo):
return True
bo[row][col] = 0
return False
def valid(bo, num, pos):
# Check row
for i in range(len(bo[0])):
if bo[pos[0]][i] == num and pos[1] != i:
return False
# Check column
for i in range(len(bo)):
if bo[i][pos[1]] == num and pos[0] != i:
return False
# Checks square
box_x = pos[1] // n
box_y = pos[0] // n
for i in range(box_y * n, box_y * n + n):
for j in range(box_x * n, box_x * n + n):
if bo[i][j] == num and (i, j) != pos:
return False
return True
def print_board(bo):
for i in range(len(bo)):
if i % n == 0 and i != 0:
print("- - - - - - - - - - - - - ")
for j in range(len(bo[0])):
if j % n == 0 and j != 0:
print(" | ", end="")
if j == m-1:
print(bo[i][j])
else:
print(str(bo[i][j]) + " ", end="")
def find_empty(bo):
for i in range(len(bo)):
for j in range(len(bo[0])):
if bo[i][j] == 0:
return i, j # return row, column
return None
def count_squares(bo):
count = 0
for box in bo:
for num in box:
if num != 0:
count += 1
return count
This function along with make_board() and solve() are used to generate the board.
def generate_board(diff):
"""generates a board based on difficulty specified"""
empty_board = [[0 for _ in range(m)] for _ in range(m)]
global counter
difficulty_levels = {"Easy": 30, "Medium": 25, "Hard": 20}
difficulty = difficulty_levels[diff]
make_board(empty_board)
counter = 1
while count_squares(empty_board) > difficulty:
x = random.randint(0, m-1)
y = random.randint(0, m-1)
if valid(empty_board, empty_board[x][y], (x, y)):
empty_board[x][y] = 0
return empty_board
board = generate_board("Hard")
print_board(board)
print("\n\n")
solve(board)
print_board(board)