Catch That CowTime Limit: 5000/2000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 4293 Accepted Submission(s): 1382
Problem Description
Farmer John has been informed of the location of a fugitive cow and wants to catch her immediately. He starts at a point N (0 ≤ N ≤ 100,000) on a number line and the cow is at a point K (0 ≤ K ≤ 100,000) on the same number line. Farmer John has two modes of transportation: walking and teleporting.
* Walking: FJ can move from any point X to the points X - 1 or X + 1 in a single minute * Teleporting: FJ can move from any point X to the point 2 × X in a single minute. If the cow, unaware of its pursuit, does not move at all, how long does it take for Farmer John to retrieve it?
Input
Line 1: Two space-separated integers: N and K
Output
Line 1: The least amount of time, in minutes, it takes for Farmer John to catch the fugitive cow.
Sample Input
Sample Output
Source
Recommend
teddy
|
=====================================算法分析=====================================
BFS+剪枝(注意数组不要越界)。
=======================================剪枝=======================================
设John的坐标为X[John],牛的坐标为X[cow]。
一、移动方法A(坐标加一)的剪枝:
一旦X[John]>X[cow],再往右走就没有意义了,因此只有在X[John]<X[cow]时才需使用移动方法A。
二、移动方法B(坐标翻倍)的剪枝:
假设:John使用移动方法B后X[John]>X[cow](即当前有2X[John]>X[cow])。
如果:1、John选择使用移动方法B,则其最小移动次数显然为1+2X[John]-X[cow]。
2、John放弃使用移动方法B,则其最小移动次数不会超过X[cow]-X[John]。
那么:需要选择移动方法B的前提是1+2X[John]-X[cow]<X[cow]-X[John]即3X[John]≤2X[cow]。
又因:2X[John]≤X[cow]的情况下3X[John]≤2X[cow]是显然成立的。
因此:只有在3X[John]≤2X[cow]时才需使用移动方法B。
=======================================代码=======================================
#include<queue>
#include<cstdio>
#include<cstring>
using namespace std;
const int MAXC=100000;
int N,K,Step[MAXC+5];
int BFS()
{
if(N==K) return 0;
memset(Step,-1,sizeof(Step));
Step[N]=0;
queue<int>q;
for(q.push(N);!q.empty();q.pop())
{
int cur=q.front();
for(int n=0;n<3;++n)
{
int tmp=cur;
if(n==0)
{
if(tmp*2<=MAXC&&tmp*3<=K*2) tmp*=2;
else continue;
}
else if(n==1)
{
if(tmp+1<=K) ++tmp;
else continue;
}
else if(n==2)
{
if(tmp-1>=0) --tmp;
else continue;
}
if(Step[tmp]==-1)
{
Step[tmp]=Step[cur]+1;
if(tmp==K) return Step[tmp];
q.push(tmp);
}
}
}
}
int main()
{
while(scanf("%d%d",&N,&K)==2)
{
printf("%d\n",BFS());
}
return 0;
}