POJ 2289 Jamis's Contact Group
2010-11-27 16:14
411 查看
一开始题目意思理解错了,其实是要求每个group最多能有几个人,我去找最大group的编号了。。。囧,size居然被我理解成那个意思。。。
正确理解题目意思后,二分答案,枚举最大值,源点与每个人连容量为1的边,每个人与他可以呆的组连一条边,然后将每个组与汇点连线,容量为枚举的最大值,如果满流就减小最大值,否则扩大最大值
代码:
正确理解题目意思后,二分答案,枚举最大值,源点与每个人连容量为1的边,每个人与他可以呆的组连一条边,然后将每个组与汇点连线,容量为枚举的最大值,如果满流就减小最大值,否则扩大最大值
代码:
#include<iostream> using namespace std; #define min(x,y) (x)<(y)?(x):(y) #define inf 99999999 #define MAX 1600 struct node { int x,y,c,op,next; }g[1000000]; int map[MAX][605],dis[MAX],pre[MAX]; int num[MAX],cur[MAX],adj[MAX],in[MAX]; int m,n,S,T,vn,max_flow,e,l,r; void add(int x,int y,int c) { e++; g[e].x=x; g[e].y=y; g[e].c=c; g[e].op=e+1; g[e].next=adj[x]; adj[x]=e; e++; g[e].x=y; g[e].y=x; g[e].c=0; g[e].op=e-1; g[e].next=adj[y]; adj[y]=e; } void relabel(int k) { int i,mm=vn; cur[k]=adj[k]; for(i=adj[k];i;i=g[i].next) { if(g[i].c>0) mm=min(mm,dis[g[i].y]); } dis[k]=mm+1; } void change() { int nf=inf,i; for(i=T;i!=S;i=g[pre[i]].x) { nf=min(nf,g[pre[i]].c); } for(i=T;i!=S;i=g[pre[i]].x) { g[pre[i]].c-=nf; g[g[pre[i]].op].c+=nf; } max_flow+=nf; } void sap() { int i; for(i=1;i<=vn;i++) { dis[i]=0; num[i]=0; cur[i]=adj[i]; } num[0]=vn; i=S; while(dis[S]<vn) { for(;cur[i];cur[i]=g[cur[i]].next) { if(g[cur[i]].c>0&&dis[i]==dis[g[cur[i]].y]+1) break; } if(!cur[i]) { num[dis[i]]--; if(num[dis[i]]==0) break; relabel(i); num[dis[i]]++; if(i!=S) i=g[pre[i]].x; } else { pre[g[cur[i]].y]=cur[i]; i=g[cur[i]].y; if(i==T) { change(); i=S; } } } } bool check(int limit) { int i,j; e=0; memset(adj,0,sizeof(adj)); S=n+m+1; T=n+m+2; vn=T; for(i=1;i<=n;i++) for(j=1;j<=m;j++) { if(map[i][j]) { add(i,n+j,1); } } for(i=1;i<=n;i++) add(S,i,1); for(i=1;i<=m;i++) { add(i+n,T,limit); } max_flow=0; sap(); if(max_flow==n) return true; else return false; } void partition() { int i,mid,ans; l=0; r=-1; for(i=1;i<=m;i++) if(in[i]>r) r=in[i]; while(l<=r) { mid=(l+r)/2; if(check(mid)) { ans=mid; r=mid-1; } else l=mid+1; } printf("%d/n",ans); } int main() { int i,t; char name[20],c; while(scanf("%d%d",&n,&m)&&m&&n) { memset(map,0,sizeof(map)); memset(in,0,sizeof(in)); for(i=1;i<=n;i++) { scanf("%s",&name); t=0; getchar(); while(scanf("%c",&c)) { if(c==10) { map[i][++t]=1; in[t]++; t=0; break; } if(c==' ') { map[i][++t]=1; in[t]++; t=0; } else t=t*10+c-'0'; } } partition(); } return 0; }
相关文章推荐
- POJ 2289 Jamie&#39;s Contact Groups &amp; POJ3189 Steady Cow Assignment
- poj 2289 Jamie's Contact Groups
- 【二分图多重匹配 && Dinic】POJ - 2289 Jamie's Contact Groups
- poj 2289 Jamie's Contact Groups 【二分 + 最大流】
- Poj-2289 Jamie's Contact Groups 多重二分图匹配
- POJ 2289 Jamie’s Contact Groups-二分匹配&多重匹配
- poj 2528 Mayor's posters 正确离散化
- POJ 3204 Ikki's Story I - Road Reconstruction 残余网络
- POJ 2449 Remmarguts' Date 第K短路 A*
- [POJ]2449. Remmarguts' Date
- POJ 2492 A Bug's Life [数据结构-并查集 union-find sets]
- POJ 2128 Leonardo's Notebook 置换群开方
- [第K短路]POJ_2449_Remmarguts' Date
- poj 3128 Leonardo's Notebook(置换的幂)
- [2-SAT] poj 3207 Ikki's Story IV - Panda's Trick
- poj-2449-Remmarguts' Date-A*+求K短路
- POJ 2528 Mayor's posters 成段更新
- 安装adt时 requires 'org.eclipse.cdt.feature.group 0.0.0' but it could not be found
- POJ 题目2528 Mayor's posters(线段树+离散化)
- POJ 1659 Frogs' Neighborhood