[网络流24题]圆桌问题
Description
假設有來自$n$個不同單位的代表參加一次國際會議。每個單位的代表數分別為$r_i(i\;\in\;[1,n])$。會議餐廳共有$m$張餐桌,每張餐桌可容納$c_i(i\;\in\;[1,m])$個代表就餐。為了使代表們充分交流,希望從同一個單位來的代表不在同一個餐桌就餐。求滿足要求的代表就餐方案。
Input
第$1$行有$2$個正整數$m,n.m$表示單位數,$n$表示餐桌數。
第$2$行有$m$個正整數,分別表示每個單位的代表數。
文件第$3$行有$n$個正整數,分別表示每個餐桌的容量。
Output
如果問題有解,第$1$行輸出$1$,否則輸出$0$。
接下來的$m$行給出每個單位代表的就餐桌號。如果有多個滿足要求的方案,只要輸出$1$個方案。
Sample Input
4 5
4 5 3 5
3 5 2 6 4
Sample Output
1
1 2 4 5
1 2 3 4 5
2 4 5
1 2 3 4 5
HINT
$1\;\leq\;m\;\leq\;150,1\;\leq\;n\;\leq\;270$
Solution
單位$i$為$x_i$,餐桌$i$為$y_i$,建立二分圖.
從$s$向$x_i$連接一條容量為$r_i$的有向邊,
從$x_i$向$y_j$連接一條容量為$1$的有向邊,
從$y_i$向$t$連接一條容量為$c_i$的有向邊,
如果最大流=人數和,則有解,從集合$x$從發流向集合$y$的滿流邊為當前方案.
#include<cmath> #include<ctime> #include<queue> #include<stack> #include<cstdio> #include<vector> #include<cstring> #include<cstdlib> #include<iostream> #include<algorithm> #define N 275 #define M 155 using namespace std; struct graph{int nxt,to,f; }e[(N*M)<<1]; int a[M],b[N],g[N+M],dep[N+M],n,m,s,t,sum,cnt=1; queue<int> q; inline void addedge(int x,int y,int f){e[++cnt].nxt=g[x];g[x]=cnt;e[cnt].to=y;e[cnt].f=f; } inline void adde(int x,int y,int f){addedge(x,y,f);addedge(y,x,0); } inline bool bfs(int u){memset(dep,0,sizeof(dep));dep[u]=1;q.push(u);while(!q.empty()){u=q.front();q.pop();for(int i=g[u];i;i=e[i].nxt)if(e[i].f>0&&!dep[e[i].to]){q.push(e[i].to);dep[e[i].to]=dep[u]+1;}}return dep[t]; } inline int dfs(int u,int f){int ret=0;if(u==t) return f;for(int i=g[u],d;i&&f;i=e[i].nxt)if(e[i].f>0&&dep[e[i].to]>dep[u]){d=dfs(e[i].to,min(f,e[i].f));e[i].f-=d;e[i^1].f+=d;ret+=d;f-=d;}return ret; } inline int dinic(){int ret=0;while(true){if(!bfs(s)) return ret;ret+=dfs(s,sum);} } inline void Aireen(){scanf("%d%d",&m,&n);s=n+m+1;t=s+1;for(int i=1;i<=m;++i){scanf("%d",&a[i]);adde(s,i,a[i]);sum+=a[i];}for(int i=1;i<=n;++i){scanf("%d",&b[i]);adde(i+m,t,b[i]);}for(int i=1;i<=m;++i)for(int j=n;j;--j)adde(i,j+m,1);if(dinic()==sum){puts("1");for(int i=1;i<=m;++i){for(int j=g[i];j;j=e[j].nxt)if(!(j&1)&&!e[j].f)printf("%d ",e[j].to-m);printf("\n");}}else puts("0");} int main(){freopen("table.in","r",stdin);freopen("table.out","w",stdout);Aireen();fclose(stdin);fclose(stdout);return 0; }轉載于:https://www.cnblogs.com/AireenYe/p/6240832.html
總結
以上是生活随笔為你收集整理的[网络流24题]圆桌问题的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 【转】增量式PID控制算法
- 下一篇: Flume在企业大数据仓库架构中位置及功