首页 > 其他 > 详细

# H - H HDU - 2066 (多起点、多终点问题)

时间:2020-04-02 14:04:34      阅读:59      评论:0      收藏:0      [点我收藏+]

H - H HDU - 2066 (多源点、多汇点问题)

一个图上,有M条边,Z个出发点,Y个终止点。求一条最短路,其中起点是Z中的任意一点,终点是Y中任意一点。

Input 输入数据有多组,输入直到文件结束。

每组的第一行是三个整数M,Z,Y

接着有M行,每行有三个整数a,b,w,表示a,b之间存在一条长度为w的边 (1=<(a,b)<=1000,w原题干未给范围c++
int够用),可能存在重边,边为双向边。

接着的第M+1行有Z个数,表示起点标号

接着的第M+2行有Y个数,表示终点标号

Output 每组数据,输出一个整数占一行表示最短路的长度

Sample Input
6 2 3
1 3 5
1 4 7
2 8 12
3 8 4
4 9 12
9 10 2
1 2
8 9 10
Sample Output
9

思路

  • 题意:给我们一个有多个出发点、多个终点的图,从任意一个出发点到任意一个终点的最短路是多少

  • 思路:类似于网络流,分别增加 相应的超级源点、和汇点,这两个点到相应的出发点、终点的边的权均为0,在跑一下 Dijkstra(更优)或者Spfa

题解

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<map>
#include<string>
#include<stack>
#include<vector>
#include<queue>
using namespace std;
#define ll long long 
#define INF 1e9
const int Len = 5000;

struct Edge
{
    int v, w, next;
} edge[Len];
int k = 0;
int head[Len];


void Add(int u, int v, int w)
{
    edge[++ k] = (Edge){ v, w, head[u] };
    head[u] = k;
}

int Spfa(int s, int e)
{
    int use[Len], dis[Len];
    for(int i = s; i <= e; i ++)
        use[i] = 0, dis[i] = INF;
    dis[s] = 0;
    queue<int> q;    
    q.push(s);
    int u, v, w;
    while(! q.empty())
    {
        u = q.front(); q.pop();
        use[u] = 0;

        for(int i = head[u]; i; i = edge[i].next)
        {
            v = edge[i].v;
            w = edge[i].w;
            if(dis[v] > dis[u] + w)
            {
                dis[v] = dis[u] + w;
                if(! use[v])
                {
                    q.push(v);
                    use[v] = 1;
                }
            }
        }
    }
    return dis[e];
}



void init()
{
    k = 0;
    memset(head, 0, sizeof(head));
}


int main()
{
    /* freopen("A.txt","r",stdin); */
    /* freopen("Ans.txt","w",stdout); */
    int m,z,y; 
    while(~ scanf("%d %d %d", &m, &z, &y))
    {
        init();
        int u, v, w;
        for(int i = 1; i <= m; i ++)
        {
            scanf("%d %d %d", &u, &v, &w);
            Add(u, v, w);
            Add(v, u, w);
        }
        int s = 0, e = 1005;
        int ver;
        for(int i = 1; i <= z; i ++)
            scanf("%d", &ver), Add(s, ver, 0);
        for(int i = 1; i <= y; i ++)
            scanf("%d", &ver), Add(ver, e, 0);

        printf("%d\n", Spfa(s, e));
    }

    return 0;
}

# H - H HDU - 2066 (多起点、多终点问题)

原文:https://www.cnblogs.com/lql-nyist/p/12619057.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!