zoukankan      html  css  js  c++  java
  • 最大获利

    链接:https://www.luogu.org/problemnew/show/P4174

    题解:

    最大权闭合子图裸题

    常规连边,砍掉一条边代表不干这件事情

    在这题中的体现就是,抉择和顾客间连INF,代表不会被砍

    顾客和t连收益,砍了说明没收益

    源和花费连边,砍了说明没花费

    注意一下数组的大小就可以了,建了8倍的边

    代码:

    #include <bits/stdc++.h>
    using namespace std;
    #define maxn 400010
    #define INF 1e9
    int n,m,c,dd,e,ans,s,t,d[maxn],head[maxn],l,b[maxn];
    bool vis[maxn];
    struct re{
        int a,b,c,flow;
    }a[maxn];
    void arr(int x,int y,int z,int flow)
    {
        a[++l].a=head[x];
        a[l].b=y;
        a[l].c=z;
        a[l].flow=flow;
        head[x]=l;
    }
    bool bfs(){
        memset(vis,0,sizeof(vis));
        queue<int> q;
        q.push(s);
        d[s]=0; vis[s]=1;
        while (!q.empty())
        {
            int x=q.front();q.pop();
            int u=head[x];
            while (u)
            {
                int v=a[u].b;
                if (!vis[v]&&a[u].c>a[u].flow)
                {
                    vis[v]=1;
                    d[v]=d[x]+1;
                    q.push(v);
                }
                u=a[u].a;
            }
        }
        return(vis[t]);
    }
    int dfs(int x,int y)
    {
        if (x==t||y==0) return y;
        int flow=0,f,tmp;
        int u=head[x];
        while (u)
        {
            int v=a[u].b;
            if (d[x]+1==d[v]&&(f=dfs(v,min(y,a[u].c-a[u].flow)))>0)
            {
                a[u].flow+=f;
                if (u%2) tmp=u+1; else tmp=u-1;
                a[tmp].flow-=f;
                flow+=f; 
                y-=f;
                if (y==0) break;
            }
            u=a[u].a;
        }
        return(flow);
    }
    int maxflow()
    {
        int flow=0;
        while (bfs())
        {
            flow+=dfs(s,INF);
        }
        return(flow);
    }
    int main()
    {
        freopen("noip.in","r",stdin);
        freopen("noip.out","w",stdout);
        cin>>n>>m; s=0; t=n+m+1;
        for (int i=1;i<=n;i++)
        { 
          cin>>b[i];
          arr(i+m,t,b[i],0); arr(t,i+m,0,0);
        }
        for (int i=1;i<=m;i++)
        {
            cin>>c>>dd>>e;
            arr(i,c+m,INF,0); arr(c+m,i,0,0);
            arr(i,dd+m,INF,0); arr(dd+m,i,0,0);
            arr(0,i,e,0); arr(i,0,0,0);
            ans+=e;
        }
        ans-=maxflow();
        cout<<ans;
    }
  • 相关阅读:
    研究动态扩容数据库解决方案
    研究分布式唯一ID生成,看完这篇就够
    聊聊心跳机制及netty心跳实现
    聊聊微服务熔断降级Hystrix
    聊聊ReentrantLock的内部实现
    Python迭代器和生成器
    Flask容器化部署原理与实现
    WSGI到底是什么?
    Tensorflow基础
    Python字典 你必须知道的用法系列
  • 原文地址:https://www.cnblogs.com/yinwuxiao/p/8438903.html
Copyright © 2011-2022 走看看