zoukankan      html  css  js  c++  java
  • 次短路问题

    题意:N 个点,R 条边,问从点 1 到点 N 的次短路为多少

    解法:首先明白次短路的计算方法:

    到某个定点 v 的次短路要么为到定点 u 的最短路加上边 (u,v)的长度;要么为到定点 u 的次短路加上边(u,v)长度。

    对于第一种情况讨论的是在松弛时没有松弛的情况,即当 dist[u] > dist[v] + cost(u,v) 时,仍然选择dist[u]。

    第二种情况比较简单,已经是次短路了,加上一条直接的边也不会更优。

     1 struct Edge {
     2     int to, weight;
     3     Edge(int to, int weight) : to(to), weight(weight) {}
     4 };
     5 vector<vector<Edge> > G(MAXN);  //更快
     6 struct Dijkstra {               //打包在Dijkstra中
     7     int n, m;
     8     bool done[MAXN];
     9     int dist[MAXN];   //最短路
    10     int dist2[MAXN];  //次短路
    11     int p[MAXN];
    12     Dijkstra(int n) : n(n) {
    13         for (int i = 1; i <= n; i++) G[i].clear();
    14     }
    15     void AddEdge(int from, int to, int weight) {
    16         G[from].push_back(Edge(to, weight));  //保存from出发的边
    17     }
    18     void dijkstra(int s) {
    19         priority_queue<pii, vector<pii>, greater<pii> > Q;
    20         memset(dist, 0x7f, sizeof(dist));  //初始化为无穷大
    21         memset(dist2, 0x7f, sizeof(dist2));
    22         memset(done, false, sizeof(done));
    23 
    24         dist[s] = 0;
    25         Q.push(pii(0, s));  // pii (dist ,u)
    26         while (!Q.empty()) {
    27             pii P = Q.top();
    28             Q.pop();
    29             int d = P.first, u = P.second;
    30             if (dist2[u] < d) continue;
    31             for (int i = 0; i < G[u].size(); i++) {
    32                 Edge& e = G[u][i];
    33                 int v = e.to, w = e.weight;
    34                 int d2 = d + w;
    35                 if (dist[v] > d2) {
    36                     swap(dist[v], d2);  // d2此时为次短路
    37                     Q.push(pii(dist[v], v));
    38                 }
    39                 if (dist2[v] > d2 && dist[v] < d2) {
    40                     dist2[v] = d2;
    41                     Q.push(pii(dist2[v], v));
    42                 }
    43             }
    44         }
    45     }
    46 };
    47 int N, R;
    48 int main() {
    49     // freopen("input.txt", "r", stdin);
    50     N = READ(), R = READ();
    51     Dijkstra Men(N);
    52     int u, v, w;
    53     REP(i, 1, R) {
    54         u = READ(), v = READ(), w = READ();
    55         Men.AddEdge(u, v, w);
    56         Men.AddEdge(v, u, w);
    57     }
    58     Men.dijkstra(1);
    59     cout << Men.dist2[N] << endl;
    60     return 0;
    61 }
  • 相关阅读:
    C#
    C#
    C#
    C#
    C#
    C#
    系统工具
    远程登录
    文件传输服务
    软件安装
  • 原文地址:https://www.cnblogs.com/romaLzhih/p/11442793.html
Copyright © 2011-2022 走看看