zoukankan      html  css  js  c++  java
  • 最小费用最大流

    #include <bits/stdc++.h>
    
    using namespace std;
    const int maxn=100010;
    const int inf=0x3f3f3f3f;
    typedef pair<int,int> PI;
    struct MCFC {
        struct edge {
            int to, next, cap, flow, cost;
        } e[maxn];
        int head[maxn], tol;
        int pre[maxn], dis[maxn];
        bool vis[maxn];
        int N;
    
        void init(int n) {
            N = n;
            tol = 1;
            memset(head, 0, sizeof(head));
        }
    
        void addedge(int u, int v, int cap, int cost) {
            tol++;
            e[tol].to = v;
            e[tol].cap = cap;
            e[tol].cost = cost;
            e[tol].flow = 0;
            e[tol].next = head[u];
            head[u] = tol;
            tol++;
            e[tol].to = u;
            e[tol].cap = 0;
            e[tol].flow = 0;
            e[tol].cost = -cost;
            e[tol].next = head[v];
            head[v] = tol;
        }
    
        bool spfa(int s, int t) {
            queue<int> q;
            for (int i = 0; i <= N; i++) {
                dis[i] = inf;
                vis[i] = false;
                pre[i] = -1;
            }
            dis[s] = 0;
            vis[s] = true;
            q.push(s);
            while (!q.empty()) {
                int u = q.front();
                q.pop();
                vis[u] = false;
                for (int i = head[u]; i; i = e[i].next) {
                    int v = e[i].to;
                    if (e[i].cap > e[i].flow && dis[v] >dis[u] + e[i].cost) {
                        dis[v] = dis[u] + e[i].cost;
                        pre[v] = i;
                        if (!vis[v]) {
                            vis[v] = true;
                            q.push(v);
                        }
                    }
                }
            }
            if (pre[t] == -1) return false;
            else return true;
        }
    
        int cost = 0;
    
        PI mcmf(int s, int t) {
            int flow = 0;
            cost = 0;
            while (spfa(s, t)) {
                int minn = inf;
                for (int i = pre[t]; i != -1; i = pre[e[i ^ 1].to]) {
                    if (minn > e[i].cap - e[i].flow) {
                        minn = e[i].cap - e[i].flow;
                    }
                }
                for (int i = pre[t]; i != -1; i = pre[e[i ^ 1].to]) {
                    e[i].flow += minn;
                    e[i ^ 1].flow -= minn;
                    cost += e[i].cost * minn;
                }
                flow += minn;
            }
            return make_pair(cost,flow);
        }
    
    } G;
    
    int main() {
        int n,m,s,t;
        scanf("%d%d%d%d", &n, &m, &s, &t);
        G.init(n);
        for (int i = 1; i <= m; i++) {
            int u, v, w, f;
            scanf("%d%d%d%d", &u, &v, &w, &f);
            G.addedge(u, v, w, f);
        }
        PI ans=G.mcmf(s, t);
        printf("%d %d
    ",ans.second,ans.first);
    }
    

      

    #include<bits/stdc++.h>
    
    using namespace std;
    typedef pair<int,int> PI;
    const int maxn=5000;
    const int inf=0x3f3f3f3f;
    int a[maxn];
    
    
    struct Min_Cost_Max_Flow{
        struct edge{
            int to,cap,cost,rev;
            edge(){};
            edge(int _to,int _cap,int _cost,int _rev):to(_to),cap(_cap),cost(_cost),rev(_rev){};
        };
        vector<edge>E[maxn];
        int h[maxn],n,d[maxn],preV[maxn],preE[maxn];
        void init(int n){
            this->n=n;
            for (int i=0;i<=n;i++){
                E[i].clear();
                h[i]=0;
            }
        }
        void add(int from,int to,int cap,int cost){
            E[from].push_back(edge(to,cap,cost,E[to].size()));
            E[to].push_back(edge(from,0,-cost,E[from].size()-1));
        }
    
        PI dijkstra(int s,int t,int f){
            int cost=0,flow=0;
            for (int i=0;i<=n;i++){
                h[i]=0;
            }
            while (f){
                priority_queue<PI,vector<PI>,greater<PI> >q;
                for (int i=0;i<=n;i++){
                    d[i]=inf;
                }
                d[s]=0;
                q.push(make_pair(0,s));
                while (!q.empty()){
                    PI now=q.top();
                    q.pop();
                    int v=now.second;
                    if (d[v]<now.first){
                        continue;
                    }
                    for (int i=0;i<E[v].size();i++){
                        edge &e=E[v][i];
                        if (e.cap>0&&d[e.to]>d[v]+e.cost+h[v]-h[e.to]){
                            d[e.to]=d[v]+e.cost+h[v]-h[e.to];
                            preV[e.to]=v;
                            preE[e.to]=i;
                            q.push(make_pair(d[e.to],e.to));
                        }
                    }
                }
                if (d[t]==inf)break;
                for (int i=0;i<=n;i++){
                    h[i]+=d[i];
                }
                int d=f;
                for (int i=t;i!=s;i=preV[i]){
                    d=min(d,E[preV[i]][preE[i]].cap);
                }
                f-=d;
                flow+=d;
                cost+=d*h[t];
                for (int i=t;i!=s;i=preV[i]){
                        edge &e=E[preV[i]][preE[i]];
                        e.cap-=d;
                        E[i][e.rev].cap+=d;
                }
            }
            return make_pair(flow,cost);
        }
    }G;
    
    int main() {
        int t,k,n;
        scanf("%d", &t);
        while (t--) {
            scanf("%d%d", &n, &k);
            for (int i = 1; i <= n; i++) {
                scanf("%d", &a[i]);
            }
            G.init(2*n+2);
            int S = 0, T = 2 * n + 2;
            G.add(S, n * 2 + 1, k, 0);
            for (int i = 1; i <= n; i++) {
                G.add(n * 2 + 1, i, 1, 0);
                G.add(i, n + i, 1, -a[i]);
                G.add(n + i, T, 1, 0);
            }
            for (int i = 1; i <= n; i++) {
                for (int j = i + 1; j <= n; j++) {
                    if (a[i] <= a[j]) {
                        G.add(n + i, j, 1, 0);
                    }
                }
            }
            PI ans=G.dijkstra(S,T,inf);
            printf("%d
    ",-ans.second);
        }
    }
    

      

  • 相关阅读:
    Message高级特性 & 内嵌Jetty实现文件服务器
    springboot中使用kindeditor富文本编辑器实现博客功能&vue-elementui使用vue-kindeditor
    Embarcadero RAD Studio XE5
    经典营销故事
    百度竞价教程 借助百度热力图让你的效果翻10倍
    无本借力:他是如何实现年收入70万?
    不用软件快速拥有几百个QQ群并都是管理员
    质保、保修、包修:含义不同
    域名反向解析在自建邮件群发服务器中的应用
    2014年1月1日,马年
  • 原文地址:https://www.cnblogs.com/Accpted/p/11203436.html
Copyright © 2011-2022 走看看