[英]Sudoku Solving - Skip on stage in backtracking
我已經在這里尋求幫助,但是沒有人回答,這確實令人沮喪,我正在嘗試編寫一個代碼來解決遞歸函數(回溯)中的數獨,這是代碼:
#include <stdio.h>
#include <windows.h>
#define SIZE 9
#define SQUARE_SIZE 3
void print(int arrBoard[SIZE][SIZE])
{
system("cls");
int i, j;
for (i = 0; i < SIZE; i++)
{
if (i % 3 == 0) printf("_ _ _ _ _ _ _ _ _ _ _ _\n");
for (j = 0; j < SIZE; j++)
{
if (j % 3 == 0) printf("| ");
printf("%d ", arrBoard[i][j]);
}
printf("\n");
}
Sleep(100);
}
BOOL IsValidRow(int arrBoard[SIZE][SIZE], int iNum, int iRow)
{
int iCol;
for (iCol = 0; iCol < SIZE; iCol++)
if (arrBoard[iRow][iCol] == iNum) return FALSE;
return TRUE;
}
BOOL IsValidCol(int arrBoard[SIZE][SIZE], int iNum, int iCol)
{
int iRow;
for (iRow = 0; iRow < SIZE; iRow++)
if (arrBoard[iRow][iCol] == iNum) return FALSE;
return TRUE;
}
BOOL IsValidSquare(int arrBoard[SIZE][SIZE], int iNum, int iRow, int iCol)
{
iRow-= (iRow % SQUARE_SIZE);
iCol-= (iCol % SQUARE_SIZE);
int i, j;
for(i = 0; i < SQUARE_SIZE; i++)
for (j = 0; j < SQUARE_SIZE; j++)
if (arrBoard[iRow + i][iCol + j] == iNum) return FALSE;
return TRUE;
}
BOOL IsValid(int arrBoard[SIZE][SIZE], int iNum, int iRow, int iCol)
{
if (IsValidRow(arrBoard, iNum, iRow) == FALSE) return FALSE;
if (IsValidCol(arrBoard, iNum, iCol) == FALSE) return FALSE;
if (IsValidSquare(arrBoard, iNum, iCol, iRow) == FALSE) return FALSE;
return TRUE;
}
BOOL _Solve(int arrBoard[SIZE][SIZE], int iRow, int iCol)
{
if (iRow == 9) return TRUE;
if (arrBoard[iRow][iCol])
{
iRow = (iCol == 8) ? iRow + 1 : iRow;
iCol = (iCol == 8) ? 0 : iCol + 1;
if(_Solve(arrBoard, iRow, iCol)) return TRUE;
return FALSE;
}
int iNewNum, iOldRow, iOldCol;
for (iNewNum = 1; iNewNum <= SIZE; iNewNum++)
{
if (IsValid(arrBoard, iNewNum, iRow, iCol))
{
arrBoard[iRow][iCol] = iNewNum;
print(arrBoard);
iOldRow = iRow; iOldCol = iCol;
iRow = (iCol == 8) ? iRow + 1 : iRow;
iCol = (iCol == 8) ? 0 : iCol + 1;
if (_Solve(arrBoard, iRow, iCol)) return TRUE;
iRow = iOldRow; iCol = iOldCol;
arrBoard[iRow][iCol] = 0;
}
}
return FALSE;
}
int main(void)
{
int arrBoard[SIZE][SIZE] =
{0, 1, 0, 3, 6, 4, 0, 2, 0,
6, 0, 0, 0, 0, 0, 0, 9, 7,
0, 0, 0, 9, 0, 7, 0, 0, 0,
0, 0, 6, 1, 0, 2, 8, 0, 0,
1, 9, 8, 0, 0, 0, 0, 3, 2,
0, 0, 7, 8, 0, 3, 9, 0, 0,
0, 0, 0, 7, 0, 8, 0, 0, 0,
4, 0, 0, 0, 0, 0, 0, 0, 3,
0, 2, 0, 4, 5, 6, 0, 1, 0};
_Solve(arrBoard, 0, 0);
fflush(stdin);
getchar();
return 0;
}
它不是真正的代碼(只是因為UI現在不重要)。 所以我在這里所做的就是每次更換任何單元時都要打印板。 我嘗試解決時遇到一個錯誤,當它到達以下行的單元格:2 col:6(在索引中的[1] [5]索引)中,它跳過了數字1(這是真正的答案),因為沒有嘗試過,它無法解決數獨的其余部分。 我找不到原因。
您已經完成了第一步,確定出現問題的位置和時間。 與調試器的幫助下,你可以通過一步_Solve
時iRow
為1和iCol
是5.這是我看到的,只是在看第一點出現時,你的問題:
IsValid(arrBoard, iNewNum, iRow, iCol)
返回FALSE
。
進入該方法后, IsValidSquare(arrBoard, iNum, iCol, iRow)
返回FALSE
。
在該行再來看,這似乎有點奇怪,你有iCol
之前iRow
下,當其他的模式是行則列。 將調用與聲明/定義進行比較,似乎您已經在調用站點混合了參數。
固定對IsValidSquare
調用的參數順序,然后重新運行即可得到解決方案。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.