zoukankan      html  css  js  c++  java
  • HDU-3416 Marriage Match IV(最短路,最大流)

    题目链接:HDU-3416 Marriage Match IV

    题意

    给出一个有向图$G$,起点$s$和终点$t$,问$s$到$t$有多少条完全不同的最短路径(即长度相同,没有公共边)。


    思路

    求最短路的条数可以用最大流,不过要去掉原图中不可能属于最短路的边。

    先用dijkstra求出各个点$u$与起点$s$的最短距离$dis[u]$,若一条边$(u,v,w)$满足$dis[v]-dis[u]==w$,说明这条边是$s o v$最短路上的边,将这样的边加入流网络,容量为1,最后求出以起点$s$为源点终点$t$为汇点的最大流就是答案。


    代码实现

    #include <iostream>
    #include <cstdio>
    #include <cstring>
    #include <queue>
    #include <utility>
    #include <vector>
    using std::pair;
    using std::queue;
    const int INF = 0x3f3f3f3f, N = 1100, M = 220000;
    int head[N], head2[N], d[N];
    int s, t, tot, tot2, maxflow;
    typedef pair<int, int> P;
    int dis[N];
    struct Edge
    {
        int to, cap, nex;
    } edge[M], edge2[M];
    queue<int> q;
    void add2(int x, int y, int z) {
        edge2[++tot2].to = y, edge2[tot2].cap = z, edge2[tot2].nex = head2[x], head2[x] = tot2;
    }
    void dijkstra() {
        std::priority_queue<P, std::vector<P>, std::greater<P> > que;
        memset(dis, INF, sizeof(dis));
        dis[s] = 0;
        que.push(P(0, s));
        while (!que.empty()) {
            P p = que.top(); que.pop();
            int v = p.second;
            if (p.first > dis[v]) continue;
            for (int i = head2[v], u; i; i = edge2[i].nex) {
                u = edge2[i].to;
                if (dis[v] + edge2[i].cap < dis[u]) {
                    dis[u] = dis[v] + edge2[i].cap;
                    que.push(P(dis[u], u));
                }
            }
        }
    }
    void add(int x, int y, int z) {
        edge[++tot].to = y, edge[tot].cap = z, edge[tot].nex = head[x], head[x] = tot;
        edge[++tot].to = x, edge[tot].cap = 0, edge[tot].nex = head[y], head[y] = tot;
    }
    bool bfs() {
        memset(d, 0, sizeof(d));
        while (q.size()) q.pop();
        q.push(s); d[s] = 1;
        while (q.size()) {
            int x = q.front(); q.pop();
            for (int i = head[x]; i; i = edge[i].nex) {
                int v = edge[i].to;
                if (edge[i].cap && !d[v]) {
                    q.push(v);
                    d[v] = d[x] + 1;
                    if (v == t) return true;
                }
            }
        }
        return false;
    }
    int dinic(int x, int flow) {
        if (x == t) return flow;
        int rest = flow, k;
        for (int i = head[x]; i && rest; i = edge[i].nex) {
            int v = edge[i].to;
            if (edge[i].cap && d[v] == d[x] + 1) {
                k = dinic(v, std::min(rest, edge[i].cap));
                if (!k) d[v] = 0;
                edge[i].cap -= k;
                edge[i^1].cap += k;
                rest -= k;
            }
        }
        return flow - rest;
    }
    void init() {
        tot = 1, tot2 = 0, maxflow = 0;
        memset(head, 0, sizeof(head));
        memset(head2, 0, sizeof(head2));
    }
    
    int main() {
        int T;
        scanf("%d", &T);
        while (T--) {
            int n, m;
            scanf("%d %d", &n, &m);
            init();
            for (int i = 0, u, v, z; i < m; i++) {
                scanf("%d %d %d", &u, &v, &z);
                if (u == v) continue;
                add2(u, v, z);
            }
            scanf("%d %d", &s, &t);
            dijkstra();
            for (int i = 1; i <= n; i++) {
                for (int j = head2[i], u; j; j = edge2[j].nex) {
                    u = edge2[j].to;
                    if (dis[u] - dis[i] == edge2[j].cap) add(i, u, 1);
                }
            }
            while (bfs()) maxflow += dinic(s, INF);
            printf("%d
    ", maxflow);
        }
        return 0;
    }
    View Code
    作者:_kangkang
    本文版权归作者和博客园共有,欢迎转载,但必须给出原文链接,并保留此段声明,否则保留追究法律责任的权利。
  • 相关阅读:
    字符编码
    python基础5
    python基础4
    python基础3
    python基础2
    一、计算机基础
    Django中间件
    Django Form表单组件
    django简介,安装,文件介绍,三板斧(render,HttpResponse,redirect)HTTP协议,用socket实现简单版web框架,用wsgiref,jinja2,pymysql实现Django运行流程
    css,浮动,清浮动,溢出overflow,定位,圆形,透明度,z-index
  • 原文地址:https://www.cnblogs.com/kangkang-/p/11339075.html
Copyright © 2011-2022 走看看