zoukankan      html  css  js  c++  java
  • HDU 6166 Spfa

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6166

    题意:
    给出一个n个点的有向图。然后给你k个点,求这k个点任意两点之间的最短路的最小值。
    思路:
    以这k个点为起点,维护每个点的最短路和次短路,并且,次短路的祖先不能是本身。

    先给几组样例:

    5
    5 6
    1 2 100
    2 5 100
    5 1 100
    3 2 100
    2 4 1
    4 3 1
    2
    1 3

    5 6
    1 2 100
    2 5 100
    5 1 100
    3 2 100
    2 4 1
    4 3 1
    2
    1 3

    4 5
    1 3 1
    3 1 1
    1 2 1000
    2 4 1
    4 2 1
    2
    1 2

    3 4
    1 2 100
    2 3 50
    1 3 1
    3 1 1
    2
    1 2

    5 6
    1 2 1
    2 3 3
    3 1 3
    2 5 1
    2 4 2
    4 3 1
    3
    1 3 5

    Case #1: 102
    Case #1: 102
    Case #3: 1000
    Case #4: 51
    Case #5: 2

    #include <bits/stdc++.h>
    using namespace std;
    typedef long long LL;
    const LL INF = 1e15;
    const int maxn = 1e5 + 15;
    int T, N, M, k;
    queue<int>que;
    struct Edge
    {
        int to, next, len;
        Edge() {}
        Edge(int to, int next, int len): to(to), next(next), len(len) {}
    } E[maxn * 4];
    int head[maxn], tot;
    void initEdge()
    {
        for(int i = 1; i <= N; i++) head[i] = -1;
        tot = 0;
    }
    void addEdge(int u, int v, int len)
    {
        E[tot] = Edge(v, head[u], len);
        head[u] = tot++;
    }
    LL dis[maxn][2];
    int ant[maxn][2];
    bool in[maxn], qr[maxn];
    int main ()
    {
        int ic = 0;
        scanf("%d", &T);
        while(T--)
        {
            scanf("%d %d", &N, &M);
            initEdge();
            for(int i = 1; i <= M; i++)
            {
                int u, v, len;
                scanf("%d %d %d", &u, &v, &len);
                addEdge(u, v, len);
            }
            for(int i = 1; i <= N; i++)//init
            {
                dis[i][0] = dis[i][1] = INF;
                ant[i][0] = ant[i][1] = -1;
                in[i] = qr[i] = false;
            }
            queue<int>que;
            scanf("%d", &k);
            for(int i = 1; i <= k; i++)
            {
                int v;
                scanf("%d", &v);
                dis[v][0] = 0;
                ant[v][0] = v;
                que.push(v), qr[v] = in[v] = true;
            }
            while(!que.empty())
            {
                int u = que.front();
                in[u] = false,que.pop();
                for(int k = head[u]; ~k; k = E[k].next)
                {
                    int v = E[k].to;
                    LL len = (LL)E[k].len + dis[u][0];
                    bool update = false;
                    if(len < dis[v][0])
                    {
                        dis[v][0] = len;
                        ant[v][0] = ant[u][0];
                        update = true;
                    }
                    else if (len < dis[v][1] && ant[u][0] != v)
                    {
                        dis[v][1] = len;
                        ant[v][1] = ant[u][0];
                        update = true;
                    }
                    len = (LL)E[k].len + dis[u][1];
                    if (len < dis[v][1] && ant[u][1] != v)
                    {
                        dis[v][1] = len;
                        ant[v][1] = ant[u][1];
                        update = true;
                    }
                    if(update&&!in[v])
                    {
                        que.push(v);
                        in[v] = true;
                    }
                }
            }
            LL ans = INF;
            for(int i=1;i<=N;i++)
                if(qr[i])   ans = min(ans,dis[i][1]);
            printf("Case #%d: %lld
    ", ++ic, ans);
        }
        return 0;
    }
  • 相关阅读:
    软件工程-事后Postmortem 会议
    软件工程-项目复审
    团队作业-冲刺博客(日更)
    团队作业-冲刺博客(任务与计划)
    团队作业-需求改进&系统设计
    软件工程团队作业-需求规格说明书
    TooBug,出撃!
    FileReader
    Javascript刷新页面的几种方法:
    软件工程-个人项目
  • 原文地址:https://www.cnblogs.com/pealicx/p/7418743.html
Copyright © 2011-2022 走看看