40. 到达目的地的最短距离(第四期模拟笔试)
原创 于 2023-10-16 17:13:38 发布 · 粉丝可见 · 262 阅读 · 1 · 0 · 本内容遵循CC 4.0 BY-SA版权协议 版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。 GEO检测 · 编辑
文章链接:https://blog.csdn.net/hacker_51/article/details/133862567
链接: 卡码网KamaCoder
题目:

样例:

思路:
这道题是求最少步数,联想一下BFS,BFS 操作可得
这是一个正向的 BFS
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91
| #include <iostream> #include <cstring> #include <algorithm> #include <queue> #include <unordered_map> #define endl '\n' #define x first #define y second #define mk make_pair #define int long long #define NO puts("NO") #define YES puts("YES") #define umap unordered_map #define INF 0x3f3f3f3f3f3f3f3f #define All(x) (x).begin(),(x).end() #pragma GCC optimize(3,"Ofast","inline") #define ___G std::ios::sync_with_stdio(false),cin.tie(0), cout.tie(0) using namespace std; const int N = 2e6 + 10; using PII = pair<int, int>;
int n;
umap<int, bool>st;
inline void op(queue<int>&q,int &now) { if (!st[now + 1]) { st[now + 1] = true; q.emplace(now + 1); } if (!st[now - 1]) { st[now - 1] = true; q.emplace(now - 1); } if (!st[now << 1]) { st[now << 1] = true; q.emplace(now << 1); } }
inline int BFS() { int step = 0; queue<int>q; q.emplace(0);
while (q.size()) { int sz = q.size(); while (sz--) { int now = q.front(); q.pop();
st[now] = true;
if (now == n) return step;
op(q,now); } ++step; } return -1; }
inline void solve() { cin >> n; cout << BFS() << endl; }
signed main() {
___G; int _t = 1;
while (_t--) { solve(); }
return 0; }
|
提交后我们可以发现:

内存超限了部分测试数据,关键点在于 操作 3 中 x = x * 2 使得 当某个数值的时候 ,使用操作3后,有可能 x > n 不必要的数据存储在了 q 中,这就是正向 BFS 的一个小缺陷
我们可以试一下 反向BFS,以 终点 为起步存储点,往 0 方向操作,此时 now 应该被整除的时候,是最佳最少步数方案的,这样可以 避免 x = x * 2 中 x > n 的数据,节省了部分空间。
代码详解如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94
| #include <iostream> #include <cstring> #include <algorithm> #include <queue> #include <unordered_map> #define endl '\n' #define x first #define y second #define mk make_pair #define int long long #define NO puts("NO") #define YES puts("YES") #define umap unordered_map #define INF 0x3f3f3f3f3f3f3f3f #define All(x) (x).begin(),(x).end() #pragma GCC optimize(3,"Ofast","inline") #define ___G std::ios::sync_with_stdio(false),cin.tie(0), cout.tie(0) using namespace std; const int N = 2e6 + 10; using PII = pair<int, int>;
int n;
umap<int, bool>st;
inline void op(queue<int>&q,int &now) { if (!st[now + 1]) { st[now + 1] = true; q.emplace(now + 1); } if (!st[now - 1]) { st[now - 1] = true; q.emplace(now - 1); } if (now % 2 == 0 && !st[now >> 1] ) { st[now >> 1] = true; q.emplace(now >> 1); } }
inline int BFS() { int step = 0; queue<int>q; q.emplace(n);
while (q.size()) { int sz = q.size(); while (sz--) { int now = q.front(); q.pop();
st[now] = true;
if (!now) return step;
op(q,now); } ++step; } return -1; }
inline void solve() { cin >> n; cout << BFS() << endl; }
signed main() {
___G; int _t = 1;
while (_t--) { solve(); }
return 0; }
|
最后提交:
