SUDOKU中的回溯失败

时间:2018-07-27 18:28:05

标签: python recursion backtracking sudoku

我一直试图在Python中实现Sudoku,但是回溯根本不起作用。当我输入一个4x4的0网格时,我得到了输出,但是大多数时候它无法提供3x3的结果。该测试用例可以正确进行,直到到达第二行的最后一个元素。

import math

solution=[[3,0,6,5,0,8,4,0,0],
          [5,2,0,0,0,0,0,0,0],
          [0,8,7,0,0,0,0,3,1],
          [0,0,3,0,1,0,0,8,0],
          [9,0,0,8,6,3,0,0,5],
          [0,5,0,0,9,0,6,0,0],
          [1,3,0,0,0,0,2,5,0],
          [0,0,0,0,0,0,0,7,4],
          [0,0,5,2,0,6,3,0,0]]

#solution=[[0 for x in range(4)] for y in range(4)]

N=9
row=0
col=0

def positionFound():
    global row,col
    for x in range(N):
        for y in range(N):
            if solution[x][y] is 0:
                row,col=x,y
                return row,col
    return False

def isSafe(row,col,num):
    global N
    for c in range(N):
        if solution[row][c] is num:
            return False
    for r in range(N):
        if solution[r][col] is num:
            return False
    r=row-row%int(math.sqrt(N))
    c=col-col%int(math.sqrt(N))

    for x in range(r,r+int(math.sqrt(N))):
        for y in range(c,c+int(math.sqrt(N))):
            if solution[x][y] is num:
                return False

    return True
back=1

def sudoku(solution):
    global row,col
    if positionFound() is False:
        print('SUCCESS')
        for x in solution:
            print(x)
        return True


    for number in range(1,N+1):
        if isSafe(row,col,number):
            solution[row][col]=number
            if sudoku(solution) is True:
                return True
            solution[row][col]=0


    return False


sudoku(solution)
for x in solution:
     print(x)

输出:

[3, 1, 6, 5, 2, 8, 4, 9, 7]
[5, 2, 4, 1, 3, 7, 8, 6, 0]
[0, 8, 7, 0, 0, 0, 0, 3, 1]
[0, 0, 3, 0, 1, 0, 0, 8, 0]
[9, 0, 0, 8, 6, 3, 0, 0, 5]
[0, 5, 0, 0, 9, 0, 6, 0, 0]
[1, 3, 0, 0, 0, 0, 2, 5, 0]
[0, 0, 0, 0, 0, 0, 0, 7, 4]
[0, 0, 5, 2, 0, 6, 3, 0, 0]

1 个答案:

答案 0 :(得分:0)

回溯不起作用的原因是您尚未实施回溯。如果您无法在给定位置放置数字,则没有准备将[row, col]光标返回到先前位置。您需要采用一种方法来知道以前的空缺职位是什么,然后用该职位的下一个合法编号恢复。您的递归保留了堆栈中以前的木板位置,但是您丢失了光标位置-并且重试循环假定它已重置。

一种很可能的方法是使rowcol成为局部变量,并使它们与它们描述的solution网格保持协调。使它们成为传递参数的一部分,以便堆栈为您维护这些值。