poj 3126 prime path 简单广搜

http://poj.org/problem?id=3126

题意:给你两个四位数a,b,从a开始    每次只能改变上一次数的其中一位,问至少需要几步才能得到b

 

分析:求最小路   典型的广搜   表面上是    40入口的bfs   但是除去有的数不是素数   入口数远小于40  

 

可以写一个  判断一个数是否为素数的函数  , 每次去 调用 判断一个数是否要进队列

也可以 事先打一个素数表  这样会快点

 

注意:output  :either with a number stating the minimal cost or containing the word Impossible

         用c++才交对的   g++  not  ok    i am confused

 

 

  1 #include <algorithm>
  2 #include <iostream>
  3 #include <sstream>
  4 #include <cstdlib>
  5 #include <cstring>
  6 #include <cstdio>
  7 #include <string>
  8 #include <bitset>
  9 #include <vector>
 10 #include <queue>
 11 #include <stack>
 12 #include <cmath>
 13 #include <list>
 14 #include <map>
 15 #include <set>
 16 using namespace std;
 17 /*10^8-----1s*/
 18 /***************************************/
 19 typedef vector<int> VI;
 20 typedef vector<char> VC;
 21 typedef vector<string> VS;
 22 typedef set<int> SI;
 23 typedef set<string> SS;
 24 typedef map<int ,int> MII;
 25 typedef map<string,int> MSI;
 26 typedef pair<int,int> PII;
 27 typedef vector<PII> VII;
 28 typedef vector<VI > VVI;
 29 /***************************************/
 30 #define min(a,b) (a>b?b:a)
 31 #define max(a,b) (a>b?a:b)
 32 
 33 #define clr(a,b) memset(a,b,sizeof(a))
 34 #define all(x)    (x).begin(), (x).end()
 35 #define sz(x) ((int)(x).size())
 36 #define ll long long
 37 #define int64 __int64
 38 #define pb push_back
 39 #define mp make_pair
 40 #define LL(x) ((x)<<1)
 41 #define RR(x) ((x)<<1|1)
 42 #define ri(x) scanf("%d",&x)
 43 #define rii(x,y) scanf("%d%d",&x,&y)
 44 #define rd(x) scanf("%lf",&x)
 45 #define rdd(x,y) scanf("%lf%lf",&x,&y)
 46 #define rs(x) scanf("%s",x)
 47 #define pi(x) printf("%d",x)
 48 #define pin(x) printf("%d\n",x)
 49 #define ps(x) printf("%s",x)
 50 #define pn()  printf("\n")
 51 #define sqr(x) ((x)*(x))
 52 #define rep(i,a,b)  for(int i=(a);i<(b);i++)
 53 #define repu(i,a,b) for(int i=(a);i<=(b);i++)
 54 #define repd(i,a,b) for(int i=(a);i>=(b);i--)
 55 #define repc(i,a,c) for(int i=(a);(c);i++)
 56 /***************************************/
 57 const int INF = 0x7f7f7f7f;
 58 const double eps = 1e-8;
 59 const double PIE=acos(-1.0);
 60 const int dx[]= {0,-1,0,1};
 61 const int dy[]= {1,0,-1,0};
 62 const int fx[]= {-1,-1,-1,0,0,1,1,1};
 63 const int fy[]= {-1,0,1,-1,1,-1,0,1};
 64 /***************************************/
 65 void openfile()
 66 {
 67     freopen("data.in","rb",stdin);
 68     freopen("data.out","wb",stdout);
 69 }
 70 /**********************The End OF The Template*****************/
 71 
 72 int primes[10004];
 73 int visit[10004];//标记 同时 记录转换的次数
 74 int a,b;
 75 int w[5];
 76 int flag;
 77 
 78 
 79 /*打表  筛选法求素数(2是最小的素数)*/
 80 void isprime()
 81 {
 82     int i,j;
 83     primes[0]=0;//等于0表示非素数
 84     primes[1]=0;
 85     for(i=2; i<=10002; i++)
 86         primes[i]=1;
 87     for(i=2; i<=10002; i++)
 88     {
 89         if(primes[i])
 90         {
 91             for(j=i+i; j<=10002; j+=i)
 92                 primes[j]=0;
 93         }
 94     }
 95 }
 96 
 97 /*广搜找最小需要的转换次数*/
 98 int bfs(int x)
 99 {
100     int xx,k,t,i,j,l;
101     queue<int >q;
102     q.push(x);
103     flag=0;
104     while(!q.empty())
105     {
106         xx=q.front();
107         q.pop();
108         if(xx==b)
109         {
110             flag=1;
111             return visit[xx];
112         }
113         w[1]=xx%10;
114         w[2]=(xx/10)%10;
115         w[3]=(xx/100)%10;
116         w[4]=xx/1000;
117 
118         for(i=1; i<=4; i++) // 1 个 2 十
119             for(j=0; j<10; j++)
120             {
121                 if(i==4&&j==0)//最高位不能为0
122                     continue;
123                 if(i==1&&j%2==0)//个位为偶数跳过
124                     continue;
125                 k=0;
126                 t=w[i];
127                 w[i]=j;
128                 for(l=4; l>0; l--)
129                 {
130                     k=k*10+w[l];
131                 }
132                 w[i]=t;
133 
134                 if(primes[k]&&!visit[k])
135                 {
136                     visit[k]=visit[xx]+1;
137                     q.push(k);
138                 }
139 
140             }
141     }
142 }
143 
144 
145 
146 int main()
147 {
148     int t;
149     isprime();
150     scanf("%d",&t);
151     while(t--)
152     {
153         memset(visit,0,sizeof(visit));
154         scanf("%d %d",&a,&b);
155         visit[a]=1;
156         int m=bfs(a);
157         if(flag)
158             printf("%d\n",m-1);
159         else
160             printf("Impossible\n");
161     }
162     return 0;
163 }
View Code

 

posted @ 2014-10-01 10:53  bibier  阅读(167)  评论(0编辑  收藏  举报