用c++代码求出有n(1<n<=100)个结点有向图中,结点1到结点n的最短路径,以及最短路径的条数。输入格式:第一行有 2 个整数n,m(0<m<3000),接下来m行每行有三个整数u,v,w,结点u到v有一条权为w的边(w<10^5)。 输出格式:输出只有一行,为结点1到结点n之间的最短路径及其条数(用空格隔开),如果1到n之间不存在路径,输出 -1 0。
时间: 2024-03-14 17:46:47 浏览: 57
C++求最短路径
以下是使用 Dijkstra 算法和 DP 计算最短路径和路径数量的 C++ 代码:
```c++
#include <iostream>
#include <vector>
#include <queue>
#include <cstring>
using namespace std;
const int INF = 0x3f3f3f3f;
const int MAXN = 105;
const int MAXM = 3005;
int n, m;
int head[MAXN], nxt[MAXM], to[MAXM], w[MAXM], edgeCnt;
void addEdge(int u, int v, int weight) {
nxt[++edgeCnt] = head[u];
head[u] = edgeCnt;
to[edgeCnt] = v;
w[edgeCnt] = weight;
}
struct Node {
int u, dis;
bool operator < (const Node& other) const {
return dis > other.dis;
}
};
int dis[MAXN], cnt[MAXN];
bool vis[MAXN];
void dijkstra(int s) {
memset(dis, INF, sizeof(dis));
memset(cnt, 0, sizeof(cnt));
memset(vis, false, sizeof(vis));
dis[s] = 0;
cnt[s] = 1;
priority_queue<Node> pq;
pq.push({s, 0});
while (!pq.empty()) {
Node cur = pq.top();
pq.pop();
int u = cur.u, d = cur.dis;
if (vis[u] || dis[u] < d) continue;
vis[u] = true;
for (int e = head[u]; e; e = nxt[e]) {
int v = to[e], weight = w[e];
if (dis[v] > dis[u] + weight) {
dis[v] = dis[u] + weight;
cnt[v] = cnt[u];
pq.push({v, dis[v]});
} else if (dis[v] == dis[u] + weight) {
cnt[v] += cnt[u];
}
}
}
}
int main() {
cin >> n >> m;
for (int i = 1; i <= m; i++) {
int u, v, weight;
cin >> u >> v >> weight;
addEdge(u, v, weight);
}
dijkstra(1);
if (dis[n] == INF) {
cout << "-1 0" << endl;
} else {
cout << dis[n] << " " << cnt[n] << endl;
}
return 0;
}
```
代码中使用了 Dijkstra 算法计算最短路径,同时使用 DP 计算路径数量。在 Dijkstra 算法的基础上,当发现一条新的最短路径时,更新到该节点的路径数量为从起点到该节点的路径数量,而当发现一条和已有最短路径等长的路径时,将路径数量加上从起点到该节点的路径数量即可。
阅读全文