LinuxSir.cn,穿越时空的Linuxsir!

 找回密码
 注册
搜索
热搜: shell linux mysql
查看: 756|回复: 3

小菜求教八皇后问题

[复制链接]
发表于 2005-4-4 23:25:22 | 显示全部楼层 |阅读模式
下面是 代码
[php]#include<stdio.h>

char Chessboard[8][8];/*声明一个二维数组,作为棋盘*/

int E_q(int x,int y,int Queens)

{   int i,j; /*用于循环计数的变量*/

    int Result=0;

    if (Queens==8)

          return 1;

    else

       if(QueenPlace(x,y))

       {

           Chessboard[x][y]='Q';

           for (i=0;i<8;i++)



                for (j=0;j<8;j++)

                {

                    Result+=E_q(i,j,Queens+1);

                    if (Result>0)

                    break;

                }

            if (Result>0)

                return 1;

            else

            {

                Chessboard[x][y]='X';

                return 0;

            }

       }

      else

          return 0;

}

/*判断是否可以放入皇后*/

int QueenPlace(int x,int y)

{

    int i,j;

    if (Chessboard[x][y]!='X')

         return 0;     /*判断本点是否有皇后*/

     for (j=y-1;j>=0;j--)

       if(Chessboard[x][j]!='X')

          return 0;    /*判断本点上面是否有皇后*/

     for  (j=y+1;j<=8;j++)

        if(Chessboard[x][j]!='X')

          return 0;    /*判断本点下面是否有皇后*/

     for (i=i-1;j>=0;i--)

        if(Chessboard[y]!='X')

          return 0;    /*判断本点左边是否有皇后*/

     for (i=i+1;i<=8;i++)

         if(Chessboard[y]!='X')

           return 0;   /*判断本点右边是否有皇后*/

       i=x-1;

       j=y-1;

       while (i>=0&&j>=0)

           if (Chessboard[i--][j--]!='X')

              return 0;

       i=x+1;

       j=y+1;

       while (i<=8&&j<=8)

            if (Chessboard[i++][j++]!='X')

              return 0;

       i=x-1;

       j=y+1;

       while (i>=0&&j<=8)

             if (Chessboard[i--][j++]!='X')

               return 0;

       i=x+1;

       j=y-1;

       while (i<=8&&j>=0)

              if (Chessboard[i++][j--]!='X')

                return 0;



       return 1;

}

void main()

{

     int i,j;

     for (i=0;i<8;i++)

     for (j=0;j<8;j++)

          Chessboard[j]='X';

      E_q(0,0,0);

      printf("the graph of 8 queens on the Chessboard.\n");

      printf("    0   1   2   3   4   5   6   7   \n");

      printf("  +---+---+---+---+---+---+---+---+---+\n");



      for (i=0;i<8;i++)

      {

        printf(" %d |",i);

        for (j=0;j<8;j++)

            printf("-%c-|",Chessboard[j]);

        printf("\n   +---+---+---+---+---+---+---+---+\n");

      }

      

}

[/php]
感觉算法和程序都没什么问题,在C-FREE下全部打印X,而用gcc 提示说段错误,高手帮忙分析一下,谢谢了
发表于 2005-4-5 10:13:56 | 显示全部楼层
太长……段错误一般是数组越界,缓冲区越界的问题。

我以前写的一个,供参考。
在win2000+borland C++ 5.0通过

  1. #include <iostream>
  2. using namespace std;

  3. int A[8][8];
  4. int size=8;
  5. int count=0;

  6. void ShowResult() //显示最后结果
  7. {
  8.         int i,j;
  9.         cout<<endl;
  10.         for(i=0;i<size;i++)
  11.         {
  12.                 for(j=0;j<size;j++)cout<<A[i][j]<<' ';
  13.                 cout<<endl;
  14.         }
  15.         count++;
  16. }


  17. void SetChessman(int xpos,int ypos,int flag) //在棋盘指定位置放上棋子
  18. {
  19.         if(flag==1)
  20.         {
  21.                 A[xpos][ypos]=1;
  22.         }
  23.         else A[xpos][ypos]=0;
  24. }


  25. bool Check(int i) //检查放置的方式是否符合8皇后要求
  26. {
  27.         int x,y,m,j;
  28.         x=y=m=j=0;
  29.         if(i>size)
  30.         {
  31.                 cout<<"error size!"<<endl;
  32.                 return false;
  33.         }
  34.         for(x=0;x<=i;x++,m=0)
  35.         {
  36.                 for(y=0;y<size;y++)
  37.                 {
  38.                         m+=A[x][y];
  39.                 }
  40.                 if(m>1)return false;

  41.         }

  42.         for(y=0;y<size;y++,m=0)
  43.         {
  44.                 for(x=0;x<=i;x++)
  45.                 {
  46.                         m+=A[x][y];
  47.                 }
  48.                 if(m>1)return false;
  49.         }

  50.         for(y=0;y<size+i;y++,m=0,j=y)
  51.         {       
  52.                 x=i;
  53.                 while(x>=0 && j>=0)
  54.                 {
  55.                         if(j<size)m+=A[x][j];
  56.                         --x;--j;
  57.                 }
  58.                 if(m>1)return false;
  59.                 m=0;
  60.                 x=0;
  61.                 j=y;

  62.                 while(x<=i && j>=0)
  63.                 {
  64.                         if(j<size)m+=A[x][j];
  65.                         ++x;--j;
  66.                 }
  67.                 if(m>1)return false;
  68.                
  69.         }
  70.         return true;
  71. }


  72. void Trial(int i) //回溯递归
  73. {
  74.         int j;
  75.         if(i>=size)ShowResult();
  76.         else for(j=0;j<size;j++)
  77.         {
  78.                 SetChessman(i,j,1);//i row, j column
  79.                 if(Check(i)==true)Trial(i+1);
  80.                 SetChessman(i,j,0);
  81.         }
  82. }


  83. void main()
  84. {
  85.         for(int i=0;i<size;i++)
  86.                 for(int j=0;j<size;j++)
  87.                         A[i][j]=0;
  88.         Trial(0);
  89.         cout<<endl<<"There are "<<count<<" kinds of resolves!"<<endl;
  90. }
复制代码

用回溯思想。
回复 支持 反对

使用道具 举报

 楼主| 发表于 2005-4-5 15:25:55 | 显示全部楼层

这个还长阿

感觉不是很长阿 ,能不能把段错误讲详细点阿 ,我 还没怎么在linux下调试程序,一头雾水,呢 ,谢谢了
回复 支持 反对

使用道具 举报

发表于 2005-4-6 09:46:00 | 显示全部楼层
粗看了一下,没有编译运行过。
数组定义是char Chessboard[8][8]
所以应该是Chessboard[0][0] 到Chessboard[7][7]
看看QueenPlace 函数中的循环:
for  (j=y+1;j<=8;j++)
while (i<=8&&j<=8)
都越界了。
问题大概就在这里吧。
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则

快速回复 返回顶部 返回列表