多重匹配即 X 集合上的点对应 Y 集合上多个点 而 Y 集合上的点对应 X 中的一个点。
/*
多重匹配问题:
解决多重匹配就是记录一下多重匹配的点(简称Y方点)已经匹配了Pi个点。
如果Pi<Ki那么就直接上了,否则的话继续搜索Yi已经匹配的每一个点并将Yi染色,
因为Yi搜一次就需要染色了,而且Y方点最多是10个,所以每次找增广路的深度最多是10,
这样就很快了!!!
*/
#include<stdio.h>
#include<algorithm>
#include<string.h>
using namespace std;
#define MAXN 100004
int n,m;
int mp[MAXN][15];
int mat[12][MAXN];
int link[15],vis[15];
int w[15];
int match(int x){
for(int i=0;i<m;i++){
if(mp[x][i]&&!vis[i]){
vis[i]=1;
if(link[i]<w[i])
{
mat[i][link[i]++]=x;
return 1;
}
for(int j=0;j<link[i];j++)
{
if(match(mat[i][j])){
mat[i][j]=x;
return 1;
}
}
}
}
return 0;
}
int hungary(){
memset(link,0,sizeof(link));
for(int i=0;i<n;i++){
memset(vis,0,sizeof(vis));
if(!match(i)) return 0;
}
return 1;
}
int main(){
while(scanf("%d%d",&n,&m)!=EOF){
memset(mp,0,sizeof(mp));
for(int i=0;i<n;i++)
for(int j=0;j<m;j++){
scanf("%d",&mp[i][j]);
}
for(int i=0;i<m;i++)
scanf("%d",&w[i]);
if(hungary())
printf("YES\n");
else printf("NO\n");
}
return 0;
}