首页 > 代码库 > bzoj 1433: [ZJOI2009]假期的宿舍 -- 最大流

bzoj 1433: [ZJOI2009]假期的宿舍 -- 最大流

1433: [ZJOI2009]假期的宿舍

Time Limit: 10 Sec  Memory Limit: 162 MB

Description

技术分享

Input

技术分享

Output

技术分享

Sample Input

1
3
1 1 0
0 1 0
0 1 1
1 0 0
1 0 0

Sample Output

ˆ ˆ

HINT

对于30% 的数据满足1 ≤ n ≤ 12。
对于100% 的数据满足1 ≤ n ≤ 50,1 ≤ T ≤ 20。

 

我们从源点向所有住宿的人连边,从所有的床位连向汇点,然后再从人连向他所认识的人的床位

这样建边,然后跑最大流

这样答案如果和住宿人数相等则满足,否则不满足

#include<cstdio>#include<cstring>#include<iostream>#include<algorithm>using namespace std;#define inf 100007#define F(i) for(i=1;i<=n;i++)#define N 50010#define M 110inline int rd(){    int x=0,f=1;char ch=getchar();    while(ch<0||ch>9){if(ch==-)f=-1;ch=getchar();}    while(ch>=0&&ch<=9){x=x*10+ch-0;ch=getchar();}    return x*f;}int lj[M],fro[N],to[N],cnt,v[N],S,T=101;inline void add(int a,int b,int c){fro[++cnt]=lj[a];to[cnt]=b;v[cnt]=c;lj[a]=cnt;}inline void ins(int a,int b,int c){add(a,b,c);add(b,a,0);}int dis[M],q[N],h,t;bool bfs(){    memset(dis,0,sizeof(dis));    dis[0]=h=t=1;q[1]=0;    int tp;    while(h<=t)    {        tp=q[h++];        for(int i=lj[tp];i;i=fro[i])        {            if(!dis[to[i]]&&v[i])            {                dis[to[i]]=dis[tp]+1;                q[++t]=to[i];            }        }    }    return dis[T]?1:0;}int dfs(int x,int p){    if(x==T) return p;    int tp,res=0;    for(int i=lj[x];i;i=fro[i])    {        if(v[i]&&dis[to[i]]==dis[x]+1)        {            tp=dfs(to[i],min(p-res,v[i]));            v[i]-=tp;             v[i^1]+=tp;            res+=tp;            if(res==p) return p;        }    }    if(res==0)  dis[x]=0;    return res;}int n,tt,sc[M],tot,ans;int main(){    tt=rd();    int i,j,x;    while(tt--)    {        tot=ans=0;        memset(lj,0,sizeof(lj));cnt=1;        n=rd();        F(i){            sc[i]=rd();            if(sc[i]) ins(i+n,T,1);        }        F(i){            x=rd();            if((sc[i]&&!x)||!sc[i])            {                ins(0,i,1);                tot++;            }        }        F(i) F(j)        {            x=rd();            if(x||i==j) ins(i,j+n,1);        }        while(bfs()) ans+=dfs(0,inf);        if(tot==ans) puts("^_^");        else puts("T_T");    }}

 

bzoj 1433: [ZJOI2009]假期的宿舍 -- 最大流