數獨問題

數獨問題

數獨是根據9*9盤面上的已知數字,推理出所有剩餘空格的數字,並滿足每一行、每一列、每一個粗線宮內的數字均含1-9,不重複。每一道合格的數獨謎題都有且僅有唯一答案。
這裏寫圖片描述
輸出該答案。

#include<stdio.h>
#define N 9

int a[N][N]={0,0,5,3,0,0,0,0,0,
             8,0,0,0,0,0,0,2,0,
             0,7,0,0,1,0,5,0,0,
             4,0,0,0,0,5,3,0,0,
             0,1,0,0,7,0,0,0,6,
             0,0,3,2,0,0,0,8,0,
             0,6,0,5,0,0,0,0,9,
             0,0,4,0,0,0,0,3,0,
             0,0,0,0,0,9,7,0,0};

bool OK(int x,int y)    //傳值爲 x,y 座標
{
    int i,j;
    int xx,yy;

    xx=x/3*3;
    yy=y/3*3;

    for(i=0;i<9;i++)    //判斷一行沒有相同元素    如果有,返回false
    {
        if(a[x][y]==a[x][i] && i!=y && a[x][i]!=0)
            return false;
    }

    for(i=0;i<9;i++)    //判斷一列沒有相同元素    如果有,返回false
    {
        if(a[x][y]==a[i][y] && i!=x && a[i][y]!=0)
            return false;
    }

    for(i=xx;i<xx+3;i++)    //判斷小九宮格    如果有,返回false
    {
        for(j=yy;j<yy+3;j++)
            if(i!=x || j!=y)  
            {  
                if(a[i][j]==a[x][y] && a[i][j]!=0)  
                    return false;  
            }
    }

    return true;
}

void backtrack(int t)   //傳參數 t 從 181 
{
    int i,j;
    int x,y;

    if(t==81)
    {
        for(i=0;i<N;i++)
        {
            for(j=0;j<N;j++)
                printf("%d ",a[i][j]);
            printf("\n");
        }
        return;
    }

    x=t/9;
    y=t%9;

    if(a[x][y]!=0)
        backtrack(t+1);
    else
    {
        for(i=1;i<10;i++)
        {
            a[x][y]=i;
            if(OK(x,y))
                backtrack(t+1);
            a[x][y]=0;
        }
    }

}

int main()
{
    backtrack(0);
    return 0;
}

/*
思路:
    定義一個9*9的數組,把已知的值填入,未知的賦值爲 0 。然後,依次從 (0,0)到(n-1,n-1)填入合適的數字。
    回溯:傳值爲 t (從 181 ),所以截止條件即爲 t=81 ,判斷座標 x=t/9y=t%9 。然後要求 每一行和每一列 都不相同進行循環判斷。再根據傳值判斷每個粗線矩形的第一個點的座標(即左上角),xx=x/3*3;,yy=y/3*3。判斷每一個小矩形內都不相同。
    可以進行剪枝:當a[x][y]=0時進行剪枝。
*/
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章