Catch That Cow (入门bfs搜索题 C语言)

题意:
农夫知道一头牛的位置,想要抓住它。农夫和牛都位于数轴上,农夫起始位于点N(0<=N<=100000),牛位于点K(0<=K<=100000)。农夫有两种移动方式:

1、从X移动到X-1或X+1,每次移动花费一分钟

2、从X移动到2*X,每次移动花费一分钟

假设牛没有意识到农夫的行动,站在原地不动。农夫最少要花多少时间才能抓住牛?

Input

两个整数,N和K

Output

一个整数,农夫抓到牛所要花费的最小分钟数

Sample Input

5 17

Sample Output

4

第一眼看到这道题如果我不知道他是搜索的话可能就会去考虑智力题或者贪心了…但转念一想贪心是每一步都取最优解,应用不到这道题上。
看了看别的大佬的思路,思路整理如下:
首先肯定不能用深搜解,TLE是肯定的。并且广搜适合用来解决“最优解”“最短路径”“最快”等这种问题。所以方法肯定是广搜。
广搜是不停地扩展树的宽度,一层一层往下遍历。这道题农夫有三种走法,也就是说可以想象成一个三叉树(但注意bfs用的数据结构是图!!)。
首先可以想到需要的是

  • quene数组(广搜标配) 搭配int head=0;int tail=1; 食用
  • book数组 如果已经入过队了就不要再入一次了

然后把广搜的模板套上,会发现,这个输出不会搞… 因为三种走法的时间都是1min,那输出搜索到next==k的时候的“树”的深度-1就行。那这个“步数计算器“,就需要一个pre数组,返回父结点,设置sum++;这个其实找出了他的路径。(具体写进周总结里了)。上源代码。

//需要一个步数计数器 
#include<stdio.h>
int que[1000000]={0};
int n,k;
int next;
int book[1000000]={0};
int pre[1000000]={0};//步数计算器

void step(int x){
	int sum=0;
	while(pre[x]){
		sum++;
		x=pre[x];
	}
	printf("%d",sum);
} 

void bfs(){
	if(n==k) {
		printf("0");
		return;//如果一开始就在一块就输出0 
	}
	int head=0;
	int tail=1;
	que[1] = n;
	book[n]=1;//队列的初始化 
	while(head != tail){
		head++;
		for(int i=1;i<=3;i++){
			if(i==1) next=que[head]-1;
			if(i==2) next=que[head]+1;
			if(i==3) next=2*que[head];
			if(next<=100000 && book[next]==0 && next>=0){//设置next的范围是怕陷入死循环且负数不能当做数组下标 
			tail++;	
			que[tail]=next;
			book[next]=1;//把入队了的一标记 
			pre[tail]=head;//记录一下父结点! 
			if(next==k){
				step(tail);
				head=tail;//强行结束while循环 
				break;
			}
		}
		}
	}
}

	int main(){
		scanf("%d%d",&n,&k);
		bfs();
	}
  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值