坐井观天

In the name of dream

导航

POJ 2243 Floyd入门

Posted on 2012-06-26 16:20  一毛_  阅读(211)  评论(0编辑  收藏  举报

题目链接: http://poj.org/problem?id=2243

题目大意:

  给定一个8×8棋盘,问骑士在棋盘中走“日”,从指定点s到指定点e所需的最小步数;

 

分析:

  看A*算法的时候,作者引用了这个例题,并且写了个A*代码,咋一看是个floyd;

  只需要把一步就可以走到的两点之间距离初始化为1,其余初始化为inf,然后跑一遍floyd就可以得出所有的最优解;

  Discuss里也有人说是纯数学题,还不理解。

  另外这题用bfs也是一样的,见我的poj1915(n<=300)的bfs代码:

poj1915
 1 /*1915    Accepted    396K    94MS    C++    1415B    2012-06-26 17:13:56*/
 2 #include <cstdio>
 3 #include <cstring>
 4 #include <cmath>
 5 #include <iostream>
 6 #include <algorithm>
 7 #include <vector>
 8 #include <queue>
 9 using namespace std;
10 
11 #define mpair make_pair
12 #define pii pair<int,int>
13 #define MM(a,b) memset(a,b,sizeof(a));
14 typedef long long lld;
15 typedef unsigned long long u64;
16 template<class T> bool up_max(T& a,const T& b){return b>a? a=b,1 : 0;}
17 template<class T> bool up_min(T& a,const T& b){return b<a? a=b,1 : 0;}
18 #define maxn 305
19 
20 int n;
21 pii st, ed;
22 bool vis[maxn][maxn];
23 typedef pair< pii, int > pi;
24 queue< pi >Q;
25 
26 int dir[8][2]= { 1,-2, 2,-1, 2,1, 1,2, -1,2, -2,1, -2,-1, -1,-2 };
27 #define x first
28 #define y second
29 int bfs(){
30     if( st==ed ) return 0;
31     while( !Q.empty() ) Q.pop();
32     MM( vis, 0 );
33     Q.push( mpair( st, 0 ) );
34     vis[st.first][st.second]= 1;
35     while( !Q.empty() ){
36         pi a= Q.front(); Q.pop();
37         for(int i=0;i<8;++i){
38             int x= a.x.x+dir[i][0], y= a.x.y+dir[i][1];
39             if( x>=0 && x<n && y>=0 && y<n && !vis[x][y] ){
40                 if( ed.x==x && ed.y==y ) return a.y+1;
41                 vis[x][y]= 1;
42                 Q.push( mpair( pii( x, y ), a.y+1 ) );
43             }
44         }
45     }
46 }
47 
48 int main()
49 {
50     //freopen("poj1915.in","r",stdin);
51     int T;
52     cin>>T;
53     while( T-- ){
54         cin>>n>>st.first>>st.second>>ed.first>>ed.second;
55         cout<< bfs() <<endl;
56     }
57 }

 

代码:

poj2243
 1 /*2243    Accepted    192K    16MS    C++    1584B    2012-06-26 16:13:06*/
 2 #include <cstdio>
 3 #include <cstring>
 4 #include <cmath>
 5 #include <iostream>
 6 #include <algorithm>
 7 #include <vector>
 8 using namespace std;
 9 
10 #define mpair make_pair
11 #define pii pair<int,int>
12 #define MM(a,b) memset(a,b,sizeof(a));
13 typedef long long lld;
14 typedef unsigned long long u64;
15 template<class T> bool up_max(T& a,const T& b){return b>a? a=b,1 : 0;}
16 template<class T> bool up_min(T& a,const T& b){return b<a? a=b,1 : 0;}
17 #define maxn
18 const int inf= 1000000000;
19 
20 pii st, ed;
21 int d[9][9][9][9];
22 int dir[8][2]={1,-2,  2,-1,  2,1,  1,2,  -1,2,  -2,1,  -2,-1,  -1,-2};
23 
24 void Init_floyd(){
25     int i,j,k,p,k1,k2;
26     for(i=0;i<8;++i)for(j=0;j<8;++j)
27             for(k=0;k<8;++k)for(p=0;p<8;++p)d[i][j][k][p]= inf;
28     for(i=0;i<8;++i)
29         for(j=0;j<8;++j){
30             d[i][j][i][j]= 0;
31             for(k=0;k<8;++k){
32                 int x= i+dir[k][0], y= j+dir[k][1];
33                 if( x>=0 && x<8 && y>=0 &&y<8 )
34                     d[i][j][x][y]= 1;
35             }
36         }
37 
38     for(i=0;i<8;++i)for(j=0;j<8;++j)
39         for(k=0;k<8;++k)for(p=0;p<8;++p)
40             for(k1=0;k1<8;++k1)for(k2=0;k2<8;++k2)
41                 up_min( d[k][p][k1][k2], d[k][p][i][j] + d[i][j][k1][k2] );
42 }
43 
44 int main()
45 {
46     //freopen("poj2243.in","r",stdin);
47     char s[5], e[5];
48     Init_floyd();
49     while( scanf("%s%s", s, e)!=EOF ){
50         st= pii( s[0]-'a', s[1]-'1' );
51         ed= pii( e[0]-'a', e[1]-'1' );
52         printf("To get from %s to %s takes %d knight moves.\n", s, e,
53             d[st.first][st.second][ed.first][ed.second]);
54     }
55 }