-
搜索的几大类型题(一)
-
寻找最短距离类
-
eg:吃奶酪
-
思路讲解:
- 本题我的思路是首先预处理:将任意两点之间的距离都算出来,再通过标记来看一下这个点是否走过,最后再通过不断更新最小值从而达到目的。
-
#include<cmath> #include<cstdio> using namespace std; int n,v[1001];//v数组——>标记是否到过此点 double x[100]; double y[20];//(x,y)——>坐标 double dis[1001][1001];//dis[i][j]——>点i到点j的距离(要预处理) double ans=1231234424.0; //保证ans比每条路径都要长 void dfs(int step,int now,double length) //step 已经走过几个点 now 当前走到的点 //length 走到的当前路径长 { if(length>ans)//剪枝(不然会超时) 当前路径已经比当前最短的要长了,就不必继续搜索, return; //直接返回上一层 if(step==n) //走完n个点 { ans=min(ans,length); //更新最短路径值 return; } for(int i=1;i<=n;i++) //枚举所有点 if(!v[i]) //没有走过 { v[i]=1; //标记为走过 dfs(step+1,i,length+dis[now][i]); //深搜下一层(好理解,不解释) v[i]=0; //回溯 从刚才上一层退回,把标记过的点取消标记 } } int main() { cin>>n; for(int i=1;i<=n;i++) cin>>x[i]>>y[i]; x[0]=0;y[0]=0; //设起点为第0个点 for(int i=0;i<=n;i++) //预处理两点间距离 for(int j=0;j<=n;j++) dis[i][j]=sqrt((x[i]-x[j])*(x[i]-x[j])+(y[i]-y[j])*(y[i]-y[j])); dfs(0,0,0.0); //已走过0个点 上一个点是第0个点 已走了长0.0的路径 printf("%.2f",ans); return 0;
}
-
- 这就是我对这道题的解法啦
虽然很垃圾 -
eg:离开中山路
这是一道很恶心 优秀的题
思路:very easy!从第一步走四个方向,不能过边界,遇到“1”就continue,直到横纵坐标均符合就可以啦!
#include<cstdio>
#include<cstring>
int fx[4]={1,0,-1,0};
int fy[4]={0,1,0,-1};
char ma[1001][1001];//注意注意!!一点要用char,输入图的时候没有空格,int输入不了
struct node{int x,y,c;}q[1100000];//(x,y)坐标,c是步数
int n;
void bfss(int stx,int sty,int enx,int eny)
//(stx,sty)起点位置,(enx,eny)终点位置
{
int tou=1,wei=2;//接下来几句就是一般的搜索了
q[tou].x=stx;q[tou].y=sty;//第一步在起点开始
q[tou].c=0;//走到起点需要0步
while(tou!=wei)
{
for(int i=0;i<4;i++)//四个方向可以走
{
int xx=q[tou].x+fx[i];//xx等于当前步q[tou].x,fx[i]是偏移量
int yy=q[tou].y+fy[i];//yy同理
if(xx==enx&&yy==eny){printf("%d",q[tou].c+1);return;}//如果走到重点,输出当前步数加1(因为走到终点也算一步),然后结束
if(xx<1||xx>n||yy<1||yy>n||ma[xx][yy]=='1') continue;//如果出界或者不能走,跳过
ma[xx][yy]='1';//走过了封路
q[wei].x=xx;//走下一步
q[wei].y=yy;//走下一步
q[wei].c=q[tou].c+1;//步数加一
wei++;//前进
}
tou++;//前进
}
}
int main()
{
scanf("%d",&n);
for(int i=1;i<=n;i++)
{
scanf("%s",ma[i]+1);//只能这样输入,用%c会有BUG,会没有输出
}
int sx,sy,ex,ey;scanf("%d %d %d %d",&sx,&sy,&ex,&ey);//输入起点终点坐标
ma[sx][sy]=1;//起点为1
bfss(sx,sy,ex,ey);//搜索
return 0;
}
做最短路径的题最好用bfs我也不知道为什么反正就是好用……
要搜最短路径需要注意的问题:
first:不要过界
second:遇到障碍要continue
third: 注意走路的四个方向
fourth:如果可以求距离最好可以预处理一下
fifth :到终点时要注意条件
sixth: 要学会运用剪枝,比如如果是走的路程已经超过最短搜到的长度了,就不用再搜下去了
先说这么几点,觉得好的可以点赞(赞赏 ) 哦!