题意:
有 m 个单位,每个单位有 r[i] 个人,有 n 张桌子,每张桌子能坐 c[i] 个人,要使同一单位的人不坐在同一张桌子,若无法满足输出 0,否则输出 1,并找到其中一种方案
题解:
怎么其他紫题都挺难的,到你这就拉了胯了啊(bushi
- 源点—>单位,流量 r[i]
- 桌子—>汇点,流量 c[i]
- 单位—>每张桌子,流量 1
算最大流是否等于 ∑ i = 1 m r i \sum_{i=1}^{m}r_i ∑i=1mri,不等于即没有满足的方案,等于就找每个单位连到桌子的边中流量为0的
#include<iostream>
#include<sstream>
#include<string>
#include<queue>
#include<map>
#include<unordered_map>
#include<set>
#include<vector>
#include<stack>
#include <utility>
#include<list>
#include<bitset>
#include<algorithm>
#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<cstring>
#include<iomanip>
#include<time.h>
#include<random>
using namespace std;
#include<ext/pb_ds/priority_queue.hpp>
#include<ext/pb_ds/tree_policy.hpp>
#include<ext/pb_ds/assoc_container.hpp>
#include<ext/pb_ds/assoc_container.hpp>
#include<ext/pb_ds/hash_policy.hpp>
using namespace __gnu_pbds;
#include<ext/rope>
using namespace __gnu_cxx;
#define int long long
#define PI acos(-1.0)
#define eps 1e-9
#define lowbit(a) ((a)&-(a))
const int mod = 1e9+7;
int qpow(int a,int b){
int ans=1;
while(b){
if(b&1)ans=(ans*a)%mod;
a=(a*a)%mod;
b>>=1;
}
return ans;
}
const int INF = 0x3f3f3f3f;
const int N = 2e6+10;
struct node{
int to,next;
int cap;
}e[N];
int head[N],cnt=1;
void add(int u,int v,int cap){
e[++cnt]={v,head[u],cap};head[u]=cnt; swap(u,v);
e[++cnt]={v,head[u],0}; head[u]=cnt;
}
int m,n,S,T,maxflow,aim;
int r[300],c[300],dis[1000];
bool bfs(){
memset(dis,0,sizeof dis);
dis[S]=1;
queue<int>q;
q.push(S);
while(!q.empty()){
int u=q.front(); q.pop();
for(int i=head[u];i;i=e[i].next){
int v=e[i].to;
if(!dis[v]&&e[i].cap){
dis[v]=dis[u]+1;
if(v==T)return 1;
q.push(v);
}
}
}
return 0;
}
int dfs(int u,int delta){
if(u==T)return delta;
int res=0;
for(int i=head[u];i&δi=e[i].next){
int v=e[i].to;
if(dis[v]==dis[u]+1&&e[i].cap){
int flow=dfs(v,min(delta,e[i].cap));
e[i].cap-=flow,e[i^1].cap+=flow;
delta-=flow,res+=flow;
}
}
return res;
}
#define endl '\n'
signed main(){
std::ios::sync_with_stdio(false);
cin.tie(0),cout.tie(0);
cin>>m>>n;
for(int i=1;i<=m;i++)cin>>r[i],aim+=r[i];
for(int i=1;i<=n;i++)cin>>c[i];
S=0,T=n+m+1;
for(int i=1;i<=m;i++)add(S,i,r[i]);
for(int i=1;i<=n;i++)add(i+m,T,c[i]);
for(int i=1;i<=m;i++)
for(int j=1;j<=n;j++)
add(i,j+m,1);
while(bfs())maxflow+=dfs(S,INF);
if(maxflow!=aim){ cout<<0<<endl; return 0;}
cout<<1<<endl;
for(int u=1;u<=m;u++){
for(int i=head[u];i;i=e[i].next){
int v=e[i].to;
if(!e[i].cap&&v!=S)cout<<v-m<<" ";
}
cout<<endl;
}
}