zoukankan      html  css  js  c++  java
  • luogu [SDOI2009]晨跑 费用流模板题

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #include<iostream>
    using namespace std;
    const int maxn=100010;
    bool vis[maxn];
    int n,m,s,t,x,y,z,f,dis[maxn],pre[maxn],last[maxn],flow[maxn],maxflow,mincost;
    //dis最小花费;pre每个点的前驱;last每个点的所连的前一条边;flow源点到此处的流量
    //maxflow 最大流量
    //mincost 最大流量的情况下的最小花费
    struct Edge
    {
        int to,next,flow,dis;//flow流量 dis花费
    } edge[maxn];
    int head[maxn],num_edge;
    queue <int> q;
    void add_edge(int from,int to,int flow,int dis)
    {
        edge[++num_edge].next=head[from];
        edge[num_edge].to=to;
        edge[num_edge].flow=flow;
        edge[num_edge].dis=dis;
        head[from]=num_edge;
    }
    bool spfa(int s,int t)
    {
        memset(dis,0x7f,sizeof(dis));
        memset(flow,0x7f,sizeof(flow));
        memset(vis,0,sizeof(vis));
        q.push(s);
        vis[s]=1;
        dis[s]=0;
        pre[t]=-1;
        while (!q.empty())
        {
            int now=q.front();
            q.pop();
            vis[now]=0;
            for (int i=head[now]; i!=-1; i=edge[i].next)
            {
                if (edge[i].flow>0 && dis[edge[i].to]>dis[now]+edge[i].dis)//正边
                {
                    dis[edge[i].to]=dis[now]+edge[i].dis;
                    pre[edge[i].to]=now;
                    last[edge[i].to]=i;
                    flow[edge[i].to]=min(flow[now],edge[i].flow);//
                    if (!vis[edge[i].to])
                    {
                        vis[edge[i].to]=1;
                        q.push(edge[i].to);
                    }
                }
            }
        }
        return pre[t]!=-1;
    }
    
    void MCMF()
    {
        while (spfa(s,t))
        {
            int now=t;
            maxflow+=flow[t];
            mincost+=flow[t]*dis[t];
            while (now!=s)
            {
                //从源点一直回溯到汇点
                edge[last[now]].flow-=flow[t];//flow和dis容易搞混
                edge[last[now]^1].flow+=flow[t];
                now=pre[now];
            }
        }
    }
    int main()
    {
        memset(head,-1,sizeof(head));
        num_edge=-1;
        cin>>n>>m;
        s=1+n,t=n;
        for (int i=1; i<=m; i++)
        {
            //z 最大流量
            //f  单位流量的费用
            int a,b,c;
            cin>>a>>b>>c;
            add_edge(a+n,b,1,c);
            add_edge(b,a+n,0,-c);
        }
        for(int i=1; i<=n; i++)
        {
            add_edge(i,i+n,1,0);
            add_edge(i+n,i,0,0);
        }
        MCMF();
        printf("%d %d",maxflow,mincost);
        return 0;
    }
  • 相关阅读:
    TFS 2013”无法移除仍为团队管理员身份的标识”
    如何在TFS的过程模板中添加报表
    集成TFS Build生成与SonarQube获取代码分析结果
    TFS 2015 Update 2功能探索
    使用Azure Automation(自动化)定时关闭和启动虚拟机
    TFS 与活动目录AD(Active Directory)的同步机制
    Eclipse 常用快捷键
    JMeter网站并发性测试
    docker安装配置GitLab
    javaWeb项目在用maven启动时必须要用到的坐标
  • 原文地址:https://www.cnblogs.com/QingyuYYYYY/p/13178367.html
Copyright © 2011-2022 走看看