hdu_1026(最短路)

题意:最快出去的路径

题解:一看就是一个很简单的最短路,用优先队列写个spfa就过了,但是没想到水了个(n*n)^2的算法也过了。。。愿意很简单,因为是个稀疏图

敲完以后一百度发现就是个简单的bfs+优先队列其实思路是一样的,每次选出不在路径中距离路径最短的边,因为这个更新的时候只能更新其周围的四个点,那个吗。。。懒得打了,。。。记得提醒我有时间打一下。。。。

代码:转化成图后,单源最短路求到n*m-1就可以了,完美

  1 #include<cstdio>
  2 #include<cstring>
  3 #include<algorithm>
  4 using namespace std;
  5 const int N = 111;
  6 #define INF 0x1fffffff
  7 char mp[N][N];
  8 int dist[N*N];
  9 bool p[N*N];
 10 int head[N*N];
 11 struct Edge{
 12     int to;
 13     int next;
 14     int w;
 15 }edge[N*N*10];
 16 int Ecnt;
 17 void init()
 18 {
 19     Ecnt = 0;
 20     memset(head,-1,sizeof(head));
 21 }
 22
 23 void printTree(int n, int m){
 24     for(int i = 0; i < n*m; i++) {
 25         printf("%d: ", i);
 26         for(int j = head[i]; j != -1; j = edge[j].next) {
 27             printf("to = %d w = %d", edge[j].to,edge[j].w);
 28         }
 29         puts("");
 30     }
 31 }
 32
 33 void add(int from, int to, int w){
 34     edge[Ecnt].to = to;
 35     edge[Ecnt].w = w;
 36     edge[Ecnt].next = head[from];
 37     head[from]=Ecnt++;
 38 }
 39 int go[4][2] = {{1,0},{-1,0},{0,1},{0,-1}};
 40 bool in(int x,int y,int n, int m){
 41     if(x<n&&x>=0&&y<m&&y>=0) return true;
 42     else return false;
 43 }
 44 int ans[N*N];
 45 int fa[N*N];
 46 int sum[N*N];
 47 void f(int n, int m){
 48     int t = 0;
 49     int tm = n*m-1;
 50     sum[t++] = n*m-1;
 51     while(fa[tm]!=0){
 52         sum[t++] = fa[tm];
 53         tm = fa[tm];
 54     }
 55     for(int i = t-1; i >= 0; i--){
 56          ans[t-i] = sum[i];
 57     }
 58 }
 59 int Count;
 60 void dijk(int s, int n)
 61 {
 62
 63     int i , j , k ;
 64     Count = 0;
 65     for(i = 0 ;i <= n ;i++)
 66     {
 67         p[i] = false;
 68         dist[i] = INF;
 69     }
 70     //p[s] = true;
 71     dist[s] = 0;
 72
 73     for( i = 0; i < n ; i++)
 74     {
 75         int Min = INF ;
 76         k = 0 ;
 77         for( j = 0 ; j < n ; j++)
 78         {
 79             if(!p[j]&&dist[j]<Min)
 80             {
 81                 Min = dist[j];
 82                 k = j;
 83             }
 84         }
 85
 86         if(Min == INF) return ;
 87         p[k] = true;
 88         //printf("k = %d\n",k);
 89         for(j = head[k]; j != -1 ; j = edge[j].next)
 90         {
 91             Edge e = edge[j];
 92             if(!p[e.to]&&dist[e.to]>dist[k]+e.w){
 93                 dist[e.to] = dist[k]+e.w;
 94                 fa[e.to] = k;
 95             }
 96         }
 97     }
 98 }
 99 int main()
100 {
101     int n,m;
102     while(~scanf("%d%d",&n,&m))
103     {
104         for(int i = 0; i < n; i++){
105             scanf("%s",&mp[i]);
106         }
107         int id;
108         init();
109         for(int i = 0; i < n; i++){
110             for(int j = 0; j < m; j++){
111                 id = i*m+j;
112                 for(int k= 0; k < 4; k++){
113                     int tx = i+go[k][0];
114                     int ty = j+go[k][1];
115                     int tid = tx*m+ty;
116                     if(in(tx,ty,n,m)){
117                         if(mp[tx][ty]==‘.‘) add(id,tid,1);
118                         else if(mp[tx][ty]==‘X‘);//add(id,tid,INF);
119                         else add(id,tid,mp[tx][ty]-‘0‘+1);
120                     }
121                 }
122             }
123         }
124        // printTree(n,m);
125         int cnt = 1;
126         int c = (n)*(m);
127         dijk(0,c);
128         f(n,m);
129
130         int t = 0;
131         if(dist[c-1]==INF) {
132             printf("God please help our poor hero.\nFINISH\n");
133             continue;
134         }
135         printf("It takes %d seconds to reach the target position, let me show you the way.\n",dist[c-1]);
136         for(int i = 1;cnt <= dist[c-1] ; i++){
137             int sx,sy,dx,dy;
138             sx = ans[t]/(m);
139             sy = ans[t++]%(m);
140             dx = ans[t]/(m);
141             dy = ans[t]%(m);
142             printf("%ds:(%d,%d)->(%d,%d)\n",cnt++,sx,sy,dx,dy);
143             if(mp[dx][dy]!=‘.‘) {
144                 for(int i = 0; i < (mp[dx][dy]-‘0‘);i++)
145                     printf("%ds:FIGHT AT (%d,%d)\n",cnt++,dx,dy);
146             }
147         }
148         puts("FINISH");
149     }
150     return 0;
151 }
时间: 2024-10-06 20:07:05

hdu_1026(最短路)的相关文章

hdu3461Marriage Match IV 最短路+最大流

//给一个图.给定起点和终点,仅仅能走图上的最短路 //问最多有多少种走的方法.每条路仅仅能走一次 //仅仅要将在最短路上的全部边的权值改为1.求一个最大流即可 #include<cstdio> #include<cstring> #include<iostream> #include<queue> #include<vector> using namespace std ; const int inf = 0x3f3f3f3f ; const

UESTC30-最短路-Floyd最短路、spfa+链式前向星建图

最短路 Time Limit: 3000/1000MS (Java/Others) Memory Limit: 65535/65535KB (Java/Others) 在每年的校赛里,所有进入决赛的同学都会获得一件很漂亮的T-shirt.但是每当我们的工作人员把上百件的衣服从商店运回到赛场的时候,却是非常累的!所以现在他们想要寻找最短的从商店到赛场的路线,你可以帮助他们吗? Input 输入包括多组数据. 每组数据第一行是两个整数NN ,MM (N≤100N≤100 ,M≤10000M≤1000

ACM: HDU 2544 最短路-Dijkstra算法

HDU 2544最短路 Time Limit:1000MS     Memory Limit:32768KB     64bit IO Format:%I64d & %I64u Description 在每年的校赛里,所有进入决赛的同学都会获得一件很漂亮的t-shirt.但是每当我们的工作人员把上百件的衣服从商店运回到赛场的时候,却是非常累的!所以现在他们想要寻找最短的从商店到赛场的路线,你可以帮助他们吗? Input 输入包括多组数据.每组数据第一行是两个整数N.M(N<=100,M<

ACM/ICPC 之 昂贵的聘礼-最短路解法(POJ1062)

//转移为最短路问题,枚举必经每一个不小于酋长等级的人的最短路 //Time:16Ms Memory:208K #include<iostream> #include<cstring> #include<cstdio> #include<cmath> #include<algorithm> using namespace std; #define INF 0x3f3f3f3f #define MAX 105 int lim, n; int p[M

图论(A*算法,K短路) :POJ 2449 Remmarguts&#39; Date

Remmarguts' Date Time Limit: 4000MS   Memory Limit: 65536K Total Submissions: 25216   Accepted: 6882 Description "Good man never makes girls wait or breaks an appointment!" said the mandarin duck father. Softly touching his little ducks' head, h

hdu4725 拆点+最短路

题意:有 n 个点,每个点有它所在的层数,最多有 n 层,相邻两层之间的点可以互相到达,消耗 c (但同一层并不能直接到达),然后还有一些额外的路径,可以在两点间互相到达,并且消耗一定费用.问 1 点到 n 点的最小花费 将每一层拆成两个点,分别为进入层和出发层,然后相邻层的出发层可以指向进入层,花费 c,每个点可以到达其出发层,而进入层可以到达该点,花费 0 ,最后建立其余双向边,最短路 1 #include<stdio.h> 2 #include<string.h> 3 #in

hdu3416 最短路+最大流

题意:有 n 点 m 边,有出发点 A 到达点 B ,只允许走原图中的最短路,但每条边只允许被走一次,问最多能找出多少条边不重复的最短路 一开始做到的时候瞎做了一发最短路,WA了之后也知道显然不对,就放着了,后来打了今年的多校,再做到的时候发现和多校第一场的1007一样的……最短路+网络流就行了,只不过第一次做这个的时候我还不知道网络流是啥,不会做也正常啦. 首先对于原图跑一遍最短路求出每个点距离 A 点的最短路,然后对于每一条边,如果它的权值等于它连接的两点的最短路的差值的时候,就说明这条路是

【啊哈!算法】算法7:Dijkstra最短路算法

上周我们介绍了神奇的只有五行的Floyd最短路算法,它可以方便的求得任意两点的最短路径,这称为“多源最短路”.本周来来介绍指定一个点(源点)到其余各个顶点的最短路径,也叫做“单源最短路径”.例如求下图中的1号顶点到2.3.4.5.6号顶点的最短路径. <ignore_js_op> 与Floyd-Warshall算法一样这里仍然使用二维数组e来存储顶点之间边的关系,初始值如下. <ignore_js_op> 我们还需要用一个一维数组dis来存储1号顶点到其余各个顶点的初始路程,如下.

HDU ACM 2544 最短路-&gt;最短路

最短路,简单题,floyd实现,在求最短路时一定要是是最大节点编号maxnum而不是输入的n,否则是错的. #include<iostream> using namespace std; int map[105][105]; //无向图 void Init() { int MAX=1000000,i,j; for(i=1;i<=104;i++) for(j=1;j<=104;j++) if(i==j) map[i][j]=0; else map[i][j]=MAX; } void