zoukankan      html  css  js  c++  java
  • N皇后问题

    要求:在一个N*N的棋盘上放置N个皇后,每行一个并使其不能互相攻击(同一行、同一列、同一斜线上的皇后都会自动攻击)。

    代码概述:

    先写一个检测是否能放皇后的函数,还有一个输出函数

    再写一个函数为执行试探的步骤

    在该函数中:

    对于合格的位置进行放置皇后检验:如果可以放置,则进行到下一行的第一个位置;如果不能放置则进行到该行的下一个位置

    对于不合格的位置,分为两种情况:

    1、行数超出:输出这种放置皇后的棋局

    2、列数超出;

    进行回退,将上一行的皇后往后挪一个位置进行检验

    #include "iostream"  
    #include "cmath"  
    using namespace std;  
      
    #define Max 20      //定义棋盘的最大值  
    int a[Max];  
    int show(int S)    //定义输出函数  
    {  
        int i,p,q;  
        int b[Max][Max]={0};     //定义并初始化b[][]输出数组  
      
        for(i=1;i<=S;i++)    //按横列i顺序输出a[i]数组坐标  
        {  
            b[i][a[i]]=1;  
            printf("(%d,%d)	",i,a[i]);  
        }  
        printf("
    ");  
        for(p=1;p<=S;p++)     //按棋盘的横列p顺序标明皇后的位置  
        {  
            for(q=1;q<=S;q++)  
            {  
                if(b[p][q]==1)     //在第p行第q列放置一个皇后棋子  
                    printf("");  
                else  
                    printf("");  
            }  
            printf("
    ");  
        }  
        return 0;  
    }  
      
    int check(int k)    //定义check函数  
    {  
        int i;  
        for(i=1;i<k;i++)    //将第k行与前面的第1~~k-1行进行判断  
        {  
            if((a[i]==a[k]) || (a[i]-a[k]==k-i) || (a[i]-a[k]==i-k))    //检查是否有多个皇后在同一条直线上  
            {  
                return 0;  
            }  
        }  
        return 1;  
    }  
      
    void check_m(int num)    //定义函数  
    {  
        int k=1,count=0;  
        printf("The possible configuration of N queens are:
    ");  
        a[k]=1;  
        while(k>0)  
        {  
            if(k<=num && a[k]<=num)    //从第k行第一列的位置开始,为后续棋子选择合适位子  
            {  
                if(check(k)==0)    //第k行的a[k]列不能放置皇后  
                {  
                    a[k]++;        //继续探测当前行的下一列:a[k]+1  
                }  
                else  
                {  
                    k++;         //第K行的位置已经确定了,继续寻找第k+1行皇后的位置  
                    a[k]=1;      //从第一列开始查找  
                }  
            }  
            else  
            {  
                if(k>num)     //若满足输出数组的要求则输出该数组  
                {  
                    count++;  
                    printf("[%d]:  ",count);  
                    show(num);    //调用输出函数show()  
                }  
                //如果k>num会执行下面两行代码,因为虽然找到了N皇后问题的一个解,但是要找的是所有解,需要回溯,从当前放置皇后的下一列继续探测  
                //如果a[k]>num也会执行下面两行代码,就是说在当前行没有找到可以放置皇后的位置,于是回溯,从上一行皇后位置的下一列继续探测  
                k--;      //棋子位置不符合要求,则退回前一步  
                a[k]++;   //继续试探下一列位置  
            }  
        }  
        printf("The count is: %d 
    ",count);  
    }  
      
    int main(void)  
    {  
        int N,d;  
        //system("color 2a");  
        do  
        {  
            printf("********************N皇后问题系统*********************
    
    ");  
            printf("                  1. 四皇后问题                        
    ");  
            printf("                  2. 八皇后问题                        
    ");  
            printf("                  3. N 皇后问题(N<20)                  
    ");  
            printf("                  4. 退出                              
    ");  
            printf("******************************************************
    ");  
            printf("
        从数字1-4之间的数选择需要的操作
    
    "); /*提示输入选项*/  
            printf("      请输入你要选择的功能选项:__
    ");  
            scanf("%d",&d);   
            switch(d)  
            {  
            case 1:  
                check_m(4);      //4皇后问题  
                break;   
            case 2:  
                check_m(8);     //8皇后问题  
                break;   
            case 3:  
                printf("请输入N的值:_");  
                fflush(stdin);      //清除缓冲  
                scanf("%d",&N);  
                printf("
    ");  
                if(N>0&&N<20)  
                {  
                    check_m(N);    //N皇后问题  
                    break;  
                }  
                else  
                {  
                    printf("输入错误,请从新输入:");  
                    printf("
    
    ");  
                    break;   
                }  
            case 4:  
                exit(0);     //程序结束  
            }  
        }while(1);  
        system("pause");  
        return 0;  
    }  

    具体原理可以参见http://blog.csdn.net/hackbuteer1/article/details/6657109

  • 相关阅读:
    HTML DOM教程 14HTML DOM Document 对象
    HTML DOM教程 19HTML DOM Button 对象
    HTML DOM教程 22HTML DOM Form 对象
    HTML DOM教程 16HTML DOM Area 对象
    ubuntu 11.04 问题 小结
    VC6.0的 错误解决办法 小结
    boot.img的解包与打包
    shell里 截取字符串
    从零 使用vc
    Imagemagick 对图片 大小 和 格式的 调整
  • 原文地址:https://www.cnblogs.com/denghui666/p/7247452.html
Copyright © 2011-2022 走看看