【洛谷习题】奇怪的电梯
题目链接:https://www.luogu.org/problemnew/show/P1135
又是水,,,但通过这道题,要知道还是有些东西需要注意的。
一开始我是用的记忆化搜索,但是爆栈了,,好迷的那种。没办法就换了BFS,又超时了!突然想到一种很简单的剪枝,才通过。
能用BFS就用吧,虽然他不太好剪枝,但做这种递推题,可以防爆栈。
另外看到有dalao用最短路做,因为这道题相当于边权为1,所以BFS和最短路是等效的。
1 #include <cstdio> 2 #include <cstdlib> 3 #include <cstring> 4 #include <queue> 5 6 using namespace std; 7 8 const int maxn = 205, inf = 0x3f3f3f3f; 9 10 struct Edge { 11 int v, next; 12 } edge[2 * maxn]; 13 14 struct node { 15 int num, step; 16 node (int n, int s) : num(n), step(s) {} 17 }; 18 19 int head[maxn], eid = 1, vis[maxn]; 20 21 queue<node> q; 22 23 inline int min(int a, int b) {return a < b ? a : b;} 24 25 void insert(int u, int v) { 26 edge[eid].v = v; 27 edge[eid].next = head[u]; 28 head[u] = eid++; 29 } 30 31 void bfs(int s, int t) { 32 q.push(node(s, 0)); 33 while (!q.empty()) { 34 int i = q.front().num, st = q.front().step; 35 q.pop(); 36 if (i == t) {printf("%d", st);exit(0);} 37 vis[i] = 1; 38 for (int j = head[i]; j; j = edge[j].next) 39 if (!vis[edge[j].v]) q.push(node(edge[j].v, st + 1)); 40 } 41 } 42 43 int main() { 44 int n, a, b, f; 45 scanf("%d%d%d", &n, &a, &b); 46 for (int i = 1; i <= n; ++i) { 47 scanf("%d", &f); 48 if (i - f >= 1) insert(i, i - f); 49 if (i + f <= n) insert(i, i + f); 50 } 51 bfs(a, b); 52 printf("-1"); 53 return 0; 54 }