zoukankan      html  css  js  c++  java
  • 2020牛客暑期多校训练营(第一场)H

    Description

    给定一个流网络 (n le 50, m le 100, sum m le 10^4)(q (sum q le 10^6)) 次询问,每次给定一个分数 (u/v),问所有边的容量是 (u/v) 时费用流的费用。

    Solution

    很自然想到把每次增广的费用都记下来,对于每个询问贪心处理即可

    #include <bits/stdc++.h>
    using namespace std;
    
    #define int long long
    const int N = 105;
    
    namespace flow {
        const int N = 205;
        const int M = 405;
        const int inf = 1e+12;
        struct Edge {
            int p, c, w, nxt = -1;
        } e[N];
        int s, t, tans, ans, cost, ind, bus[N], qhead = 0, qtail = -1, qu[M],vis[N], dist[N];
    
        void graph_link(int p, int q, int c, int w) {
            e[ind].p = q;
            e[ind].c = c;
            e[ind].w = w;
            e[ind].nxt = bus[p];
            bus[p] = ind;
            ++ind;
        }
        void make(int p, int q, int c, int w) {
            graph_link(p, q, c, w);
            graph_link(q, p, 0, -w);
        }
        int dinic_spfa() {
            qhead = 0;
            qtail = -1;
            memset(vis, 0x00, sizeof vis);
            memset(dist, 0x3f, sizeof dist);
            vis[s] = 1;
            dist[s] = 0;
            qu[++qtail] = s;
            while (qtail >= qhead) {
                int p = qu[qhead++];
                vis[p] = 0;
                for (int i = bus[p]; i != -1; i = e[i].nxt)
                    if (dist[e[i].p] > dist[p] + e[i].w && e[i].c > 0) {
                        dist[e[i].p] = dist[p] + e[i].w;
                        if (vis[e[i].p] == 0)
                            vis[e[i].p] = 1, qu[++qtail] = e[i].p;
                    }
            }
            return dist[t] < inf;
        }
        int dinic_dfs(int p, int lim) {
            if (p == t)
                return lim;
            vis[p] = 1;
            int ret = 0;
            for (int i = bus[p]; i != -1; i = e[i].nxt) {
                int q = e[i].p;
                if (e[i].c > 0 && dist[q] == dist[p] + e[i].w && vis[q] == 0) {
                    int res = dinic_dfs(q, min(lim, e[i].c));
                    cost += res * e[i].w;
                    e[i].c -= res;
                    e[i ^ 1].c += res;
                    ret += res;
                    lim -= res;
                    if (lim == 0)
                        break;
                }
            }
            return ret;
        }
        vector<int> solve(int _s,int _t) {
            s=_s; t=_t;
            vector <int> vec;
            int oldcost=0;
            cost=0;
            ans=0;
            while (dinic_spfa()) {
                memset(vis, 0x00, sizeof vis);
                ans += dinic_dfs(s, inf);
                vec.push_back(cost-oldcost);
                oldcost=cost;
            }
            return vec;
        }
        void init() {
            memset(bus, 0xff, sizeof bus);
            ind=0;
        }
    }
    
    int n,m,q,t1,t2,t3;
    
    void solve()
    {
        flow::init();
        for(int i=1;i<=m;i++)
        {
            scanf("%lld%lld%lld",&t1,&t2,&t3);
            flow::make(t1,t2,1,t3);
        }
        vector<int> vec = flow::solve(1,n);
        vector<int> sum = vec;
        for(int i=1;i<sum.size();i++) sum[i]+=sum[i-1];
        scanf("%lld",&q);
        for(int i=1;i<=q;i++)
        {
            int u,v; //u/v
            scanf("%lld%lld",&u,&v);
            int g;
            if(flow::ans * u < v)
            {
                puts("NaN");
                continue;
            }
            int _v=v;
            int a0=1;
            int ans=0;
            int pos=v/u;
            v-=pos*u;
            if(pos) ans+=sum[pos-1]*u;
            ans+=vec[pos]*v;
            a0*=_v;
            g=__gcd(a0,ans);
            if(g) a0/=g, ans/=g;
            printf("%lld/%lld
    ",ans,a0);
        }
    }
    
    signed main()
    {
        ios::sync_with_stdio(false);
        while(~scanf("%lld%lld",&n,&m))
        {
            solve();
        }
    }
    
    
  • 相关阅读:
    如何更高效(HOWTO: Be more productiveAaron Swartz)
    这事儿太丢人了
    2012年终极心愿之每月培养一个好习惯
    【转载】SQLLite使用入门
    【原创】XNA 4.0学习笔记之如何使用XACT给Cue添加多个音频
    【原创】编程日记之——如何对DataSet进行强类型化
    【索引】Win7 操作系统编程常识
    [原创]怎么降低Winform程序占用的内存
    【原创】自制Winform标签控制控件[支持不规则窗体]
    【原创】XNA 4.0学习笔记之绘制基元图形的几种PrimitiveType区别[PS:4.0似乎有所改动]
  • 原文地址:https://www.cnblogs.com/mollnn/p/13305640.html
Copyright © 2011-2022 走看看