HDU 2063 BNUOJ 6207 过山车 (最大流or二分匹配)

来源:互联网 发布:java构造器 编辑:程序博客网 时间:2024/06/07 16:19

满足二分图矛盾的性质,女生编号为1~M,男生则为M+1~M+N,输入时处理,然后直接建边,求出最大匹配数即为答案。

#include <iostream>#include <cstdio>#include <cstring>#include <cmath>#include <vector>#include <algorithm>#include <queue>using namespace std;int k,n,m,u,v;int c[1005],linker[1005];;vector <int> G[1005];bool dfs(int u){    int len=G[u].size();    for(int i=0;i<len;++i)    {        int v=G[u][i];        if(!c[v])        {            c[v]=1;            if(dfs(linker[v])||linker[v]==-1)            {                linker[v]=u;                return true;            }        }    }    return false;}int main(){    while(scanf("%d",&k)==1&&k)    {        scanf("%d%d",&n,&m);        for(int i=0;i<=n+m;++i)G[i].clear();        for(int i=0;i<k;++i)        {            scanf("%d%d",&u,&v);            u--;v--;v+=n;            G[u].push_back(v);            G[v].push_back(u);        }        int ans=0;        memset(linker,-1,sizeof(linker));        for(int i=0;i<n+m;++i)        {            memset(c,0,sizeof(c));            if(dfs(i))ans++;        }        cout<<ans/2<<endl;    }    return 0;}

考虑最大流做,源点与女孩建流量1的边,女孩到男孩建流量1的边,男孩到汇点建流量1的边,跑最大流。

#include <iostream>#include <cstdio>#include <cstring>#include <cmath>#include <vector>#include <algorithm>#include <queue>#include <set>using namespace std;const int INF=0x3f3f3f3f;const int MAXN=2000;const int MAXM=10005;int n,m,u,v,w;struct Edge{    int to,next,flow;}edge[MAXM];int head[MAXN],tot;void add(int u,int v,int w){    edge[tot].to=v;    edge[tot].flow=w;    edge[tot].next=head[u];    head[u]=tot++;    edge[tot].to=u;    edge[tot].flow=0;    edge[tot].next=head[v];    head[v]=tot++;}int dep[MAXN];bool bfs(int s,int t){    int u;    memset(dep,-1,sizeof(dep));    queue <int> q;    q.push(s);    dep[s]=0;    while(!q.empty())    {        u=q.front();        q.pop();        for(int i=head[u];~i;i=edge[i].next)        {            int v=edge[i].to;            if(dep[v]==-1&&edge[i].flow>0)            {                dep[v]=dep[u]+1;                if(v==t)return true;                q.push(v);            }        }    }    return false;}int dfs(int s,int t,int x){    if(s==t)return x;int ans=x;    for(int i=head[s];~i;i=edge[i].next)    {        int v=edge[i].to;        if(dep[v]==dep[s]+1&&edge[i].flow>0)        {            int minn=dfs(v,t,min(x,edge[i].flow));            edge[i].flow-=minn;            edge[i^1].flow+=minn;            x-=minn;        }    }    return ans-x;}int dinic(){    int ans=0;    while(bfs(1,n))ans+=dfs(1,n,INF);    return ans;}int main(){    //freopen("in.txt","r",stdin);    int a,b,k;    while(scanf("%d",&k)==1&&k)    {        scanf("%d%d",&a,&b);        tot=0;n=a+b+2;        memset(head,-1,sizeof(head));        for(int i=0;i<k;++i)        {            scanf("%d%d",&u,&v);            add(u+1,v+a+1,1);        }        for(int i=0;i<a;++i)        {            add(1,i+2,1);        }        for(int i=0;i<b;++i)        {            add(i+a+2,n,1);        }        printf("%d\n",dinic());    }    return 0;}
0 0
原创粉丝点击