HDU 4292 Food(最大流)
http://acm.hdu.edu.cn/showproblem.php?pid=4292
题意:n个人,m1个食物,m2个饮料,要求每个人都拿到一份饮料和一份食物,求最大满足数。
思路:S向食物连边,流量为食物数量。饮料向T连边,流量为饮料数量。
人拆点,限流为1,食物向人连边,流量为1,人向饮料连边,流量为1.
注意:每次新建图的时候要把dis和cnt数组清零。。而且要看一下数据范围才开数组。
1 #include <algorithm> 2 #include <iostream> 3 #include <cstdio> 4 #include <cstdlib> 5 #include <cstring> 6 #include <string> 7 #include <queue> 8 #include <ctime> 9 #include <cmath> 10 #include <map> 11 #define inf 0x7fffffff 12 int tot,go[1200005],first[200005],next[1200005]; 13 int flow[1200005],op[1200005],dis[200005],cnt[200005]; 14 int n,m1,m2,S,T,nodes; 15 int read(){ 16 char ch=getchar();int t=0,f=1; 17 while (ch<'0'||ch>'9'){if (ch=='-') f=-1;ch=getchar();} 18 while ('0'<=ch&&ch<='9'){t=t*10+ch-'0';ch=getchar();} 19 return t*f; 20 } 21 void insert(int x,int y,int z){ 22 tot++; 23 go[tot]=y; 24 next[tot]=first[x]; 25 first[x]=tot; 26 flow[tot]=z; 27 } 28 void add(int x,int y,int z){ 29 insert(x,y,z);op[tot]=tot+1; 30 insert(y,x,0);op[tot]=tot-1; 31 } 32 int dfs(int x,int f){ 33 if (x==T) return f; 34 int mn=nodes+1,sum=0; 35 for (int i=first[x];i;i=next[i]){ 36 int pur=go[i]; 37 if (dis[pur]+1==dis[x]&&flow[i]){ 38 int save=dfs(pur,std::min(f-sum,flow[i])); 39 flow[i]-=save; 40 flow[op[i]]+=save; 41 sum+=save; 42 if (sum==f||dis[S]>=nodes) return sum; 43 } 44 if (flow[i]) mn=std::min(mn,dis[pur]); 45 } 46 if (sum==0){ 47 cnt[dis[x]]--; 48 if (cnt[dis[x]]==0){ 49 dis[S]=nodes; 50 }else{ 51 dis[x]=mn+1; 52 cnt[dis[x]]++; 53 } 54 } 55 return sum; 56 } 57 int main(){ 58 while (scanf("%d",&n)!=EOF){ 59 m1=read();m2=read(); 60 tot=0;memset(first,0,sizeof first); 61 memset(dis,0,sizeof dis); 62 memset(cnt,0,sizeof cnt); 63 S=0;T=n+m1+m2+1+n;nodes=T+1; 64 for (int i=1;i<=m1;i++){ 65 int x=read(); 66 add(S,i+2*n,x); 67 } 68 for (int i=1;i<=m2;i++){ 69 int x=read(); 70 add(n*2+m1+i,T,x); 71 } 72 char s[200005]; 73 for (int i=1;i<=n;i++){ 74 scanf("%s",s+1); 75 for (int j=1;j<=m1;j++) 76 if (s[j]=='Y') add(j+2*n,i,1); 77 } 78 for (int i=1;i<=n;i++) 79 add(i,i+n,1); 80 for (int i=1;i<=n;i++){ 81 scanf("%s",s+1); 82 for (int j=1;j<=m2;j++) 83 if (s[j]=='Y') add(i+n,j+2*n+m1,1); 84 } 85 int ans=0; 86 while (dis[S]<nodes) ans+=dfs(S,inf); 87 printf("%d\n",ans); 88 } 89 }