zoukankan      html  css  js  c++  java
  • poj2584T-Shirt——网络最大流

    题目:http://poj.org/problem?id=2584

    以人和衣服作为点,建立超级源点和超级汇点,人连边权为1的边,衣服对源点连边权为件数的边(别弄乱顺序);

    试图写构造函数,但CE了,最后只好用冗杂的写法。

    代码如下:

    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<queue>
    using namespace std;
    queue<int>q;
    int n,head[30],ct=1,d[30],cur[30],INF=1e9,s,t;
    char dc[105];
    struct N{
        int to,next,w;
    }edge[705];
    //struct N{
    //    int next,to,w;
    //    N(int a=0,int b=0,int c=0):next(a),to(b),w(c) {}
    //}edge[255];
    int ex(char cc)
    {
        if(cc=='S')return 1;
        if(cc=='M')return 2;
        if(cc=='L')return 3;
        if(cc=='X')return 4;
        if(cc=='T')return 5;
    }
    void ad(int x,int y,int z)
    {
    //    edge[++ct]=(N){y,head[x],z};head[x]=ct;
    //    edge[++ct]=(N){x,head[y],0};head[y]=ct;
        edge[++ct].to=y;
        edge[ct].next=head[x];
        edge[ct].w=z;
        head[x]=ct;
        edge[++ct].to=x;
        edge[ct].next=head[y];
        edge[ct].w=0;
        head[y]=ct;
    //    edge[++ct]=N{y,head[x],z};head[x]=ct;
    //    edge[++ct]=N{x,head[y],0};head[y]=ct;
    }
    void add(int p,char c[])
    {
        int x=n+ex(c[0]);
        int y=n+ex(c[1]);
        for(int i=x;i<=y;i++)ad(i,p,1);
    }
    bool bfs()
    {
        memset(d,0,sizeof d);
        while(q.size())q.pop();
        q.push(0);d[0]=1;
        while(q.size())
        {
            int x=q.front();q.pop();
            for(int i=head[x];i;i=edge[i].next)
            {
                int u=edge[i].to;
                if(!d[u]&&edge[i].w)
                {
                    d[u]=d[x]+1;
                    q.push(u);
                }
            }
        }
        return d[t];
    }
    int dfs(int x,int f)
    {
        if(x==t)return f;
        int res=0;
        for(int i=cur[x];i;i=edge[i].next)
        {
            int u=edge[i].to;
            if(d[u]==d[x]+1&&edge[i].w)
            {
                int tmp=dfs(u,min(edge[i].w,f-res));
                edge[i].w-=tmp;
                edge[i^1].w+=tmp;
                res+=tmp;
                if(edge[i].w)cur[x]=i;
                if(res==f)return f;
            }
        }
        if(!res)d[x]=0;//剪枝 
        return res;
    }
    bool dinic()
    {
        int ret=0;
        while(bfs())
        {
            for(int i=s;i<=t;i++)cur[i]=head[i];
            ret+=dfs(s,INF);
        }
        if(ret==n)return 1;
        else return 0;
    }
    int main()
    {
        while(1)
        {
            cin>>dc;
            if(dc[0]=='E')return 0;
            ct=1;//!
            memset(head,0,sizeof head);
            scanf("%d ",&n);
            for(int i=1;i<=n;i++)
            {
                cin>>dc;
                add(i,dc);
            }
            for(int i=n+1;i<=n+5;i++)
            {
                int x;
                scanf("%d",&x);
                ad(0,i,x);//0为超级源点 
            }
            for(int i=1;i<=n;i++)ad(i,n+6,1);//n+6为超级汇点 
            s=0;t=n+6;
            cin>>dc;
            if(dinic())printf("T-shirts rock!
    ");
            else printf("I'd rather not wear a shirt anyway...
    ");
        }
        return 0;
    }
  • 相关阅读:
    事务
    触发器
    入行大数据必须知道的事!
    5G如何使云计算更加前卫
    2021年加密货币和区块链风向
    2020年数据存储管理发生的7种变化
    如何克服物联网中数据集成的挑战
    从开发到产出:关于机器学习的七则干货建议
    如何利用机器学习进行静态分析
    AI如何改变DevOps?
  • 原文地址:https://www.cnblogs.com/Zinn/p/8606010.html
Copyright © 2011-2022 走看看