zoukankan      html  css  js  c++  java
  • 【BZOJ4950】lydsy七月月赛 C 二分图最大匹配

    【BZOJ4950】lydsy七月月赛 C

    题面

    题解:比较直接的想法就是:每行,每列的最大值都留下,剩下的格子都变成1。但是如果一个格子既是行的最大值又是列的最大值,那么我们只需要把它留下即可。这就变成了一个二分图最大匹配问题,乱搞即可。

    #include <cstdio>
    #include <cstring>
    #include <iostream>
    using namespace std;
    typedef long long ll;
    int n,m,cnt,now;
    ll ans;
    ll map[110][110],s1[110],s2[110];
    int to[10010],next[10010],head[110],vis[110],from[110];
    void add(int a,int b)
    {
    	to[++cnt]=b,next[cnt]=head[a],head[a]=cnt;
    }
    int dfs(int x)
    {
    	for(int i=head[x];i;i=next[i])
    	{
    		if(vis[to[i]])	continue;
    		vis[to[i]]=1;
    		if(!from[to[i]]||dfs(from[to[i]]))
    		{
    			from[to[i]]=x;
    			return 1;
    		}
    	}
    	return 0;
    }
    int main()
    {
    	scanf("%d%d",&n,&m);
    	int i,j;
    	for(i=1;i<=n;i++)	for(j=1;j<=m;j++)
    		scanf("%lld",&map[i][j]),s1[i]=max(s1[i],map[i][j]),s2[j]=max(s2[j],map[i][j]),ans+=map[i][j];
    	for(i=1;i<=n;i++)	for(j=1;j<=m;j++)
    	{
    		if(map[i][j])
    		{
    			ans--;
    			if(s1[i]>1&&s1[i]==s2[j])	add(i,j);
    		}
    	}
    	for(i=1;i<=n;i++)	if(s1[i])	ans-=s1[i]-1;
    	for(i=1;i<=m;i++)	if(s2[i])	ans-=s2[i]-1;
    	for(i=1;i<=n;i++)	if(s1[i])	memset(vis,0,sizeof(vis)),ans+=dfs(i)*(s1[i]-1);
    	printf("%lld",ans);
    	return 0;
    }
  • 相关阅读:
    Notes of Daily Scrum Meeting(12.22)
    一个合格的程序员应该读过哪些书
    snprintf vs sprintf
    Centos 关闭图形界面
    oracle selinux 问题
    struct 和typedef struct的区别
    c语言字符串函数
    504. Base 7
    汉诺塔python实现
    VIM字符编码基础知识
  • 原文地址:https://www.cnblogs.com/CQzhangyu/p/7265270.html
Copyright © 2011-2022 走看看