My Carelessness

Back to your page!


Or leave your comments here.

RegendLa

导航

关于回溯与走八方

  有个汉子,和一匹马,从5*5的棋盘一角出发,要走完棋盘的每一个角落,对没错,每一个角落。输出所有的走法。如:

    输出格式示例:
      1    16   21   10   25
      20  11   24   15    22
      17  2     19   6     9
      12  7     4     23   14
      3   18    13   8     5
  示例中的数字代表的是所走的步数。

  首先,我们知道马在棋盘上正常情况下共有八个可走的方向,这八个方向会在回溯算法中多次调用,所以我们可以用两个数组来储存它们。然后就是进行遍历,判断按照该方向下一步是否会越界,若不会越界,则 判断该方向下一步是否已经走过,若走过(标志变量被修改为了所走的步数),则换一个方向,若没走过(标志变量为0),则将该位置标记。然后重复该过程,若遍历了所有的方向,不用小子说大家也懂,那就回溯一步。

  来看看代码:

 1 #include<stdio.h>
 2 int sum=0;
 3 int board[5][5]={0};
 4 int x[8]={1,2,2,1,-1,-2,-2,-1};//储存八个方向 
 5 int y[8]={2,1,-1,-2,2,1,-1,-2};//储存八个方向 
 6 void out();//输出函数 
 7 void f(int k,int a,int b);//k统计步数,a为上一位置的横坐标,b为上一位置的纵坐标 
 8 int main()
 9 {
10     board[0][0]=1;
11     f(2,0,0);
12     return 0;
13 }
14 void f(int k,int a,int b)
15 {
16     int i;
17     for(i=0;i<=7;i++)
18     {
19         if( (a+x[i]>=0) && (a+x[i]<=4) //判断该方向下一步的横坐标是否越界 
20          && (b+y[i]>=0) && (b+y[i]<=4) /*判断该方向下一步的纵坐标是否越界*/)
21         {
22             if(board[a+x[i]][b+y[i]]==0)
23             {
24                 board[a+x[i]][b+y[i]]=k;
25                 if(k==25)
26                     out();
27                 else
28                     f(k+1,a+x[i],b+y[i]);
29                 board[a+x[i]][b+y[i]]=0;
30             }
31         }
32     }
33 }
34 void out()
35 {
36     int i,j;
37     sum++;
38     printf("第%d种走法:\n",sum);
39     for(j=0;j<=4;j++)
40     {
41         for(i=0;i<=4;i++)
42         {
43             printf("%d\t",board[i][j]);
44         }
45         printf("\n");
46     }
47 }
48 //注意,若按照该代码进行,将不能达成题目的输出所有解的要求,若想达成此要求,则需要同学自行使用重定向(freopen)输出

  代码如有不足之处,欢迎指出!

posted on 2015-05-26 17:18  最爱七  阅读(244)  评论(1编辑  收藏  举报




Thanks for your coming!
If what you read helps,I would appreciate!