洛谷P1144 最短路计数 题解 无权图的最短路计数(广搜)
题目链接:https://www.luogu.com.cn/problem/P1144
题目大意:
给你一个无向无权图,求点 \(1\) 到所有点的最短路的方案数。
解题思路:
因为是无权图,所以可以使用广搜来求最短路,然后在广搜的过程中,定义:
- \(dist[u]\) 表示点 \(1\) 到点 \(u\) 的最短路距离;
- \(f[u]\) 表示点 \(1\) 到点 \(u\) 的最短路方案数。
则:
\[f[v] = \sum_{u \rightarrow v} f[u]
\]
其中,要满足 \(dist[u] + 1 = dist[v]\)。
实现代码如下:
#include <bits/stdc++.h>
using namespace std;
const int maxn = 1000010, MOD = 100003;
int n, m, dist[maxn], f[maxn];
vector<int> g[maxn];
queue<int> que;
void bfs() {
memset(dist, -1, sizeof(dist));
dist[1] = 0;
f[1] = 1;
que.push(1);
while (!que.empty()) {
int u = que.front();
que.pop();
int sz = g[u].size();
for (int i = 0; i < sz; i ++) {
int v = g[u][i];
if (dist[v] == -1) {
dist[v] = dist[u] + 1;
f[v] = f[u];
que.push(v);
}
else if (dist[v] == dist[u] + 1) {
f[v] = (f[v] + f[u]) % MOD;
}
}
}
for (int i = 1; i <= n; i ++) cout << f[i] << endl;
}
int main() {
cin >> n >> m;
while (m --) {
int a, b;
cin >> a >> b;
g[a].push_back(b);
g[b].push_back(a);
}
bfs();
return 0;
}