JT的难题(匹配问题 最大独立集)

https://turingjudge.com/contest/3/problem/1002
QkCvNnnjg5

题意:

在一个棋盘上给出一些马,问最少删掉几个使得两两不能吃。

解析:

如果是一对一冲突,输出方案是2SAT问题。
如果是一对多输出,输出最大数量,是最大独立集问题。

最少删掉几个就是最多留下几个,也就是最大独立集。

将冲突的马之间匹配上,求一个最大独立集(n-最大匹配)。
由于不是二分图,可以左边n个,右边n个,最后除2即可。

代码:

/*
 *  Author : Jk_Chen
 *    Date : 2020-04-20-09.52.15
 */
#include<bits/stdc++.h>
using namespace std;
#define LL long long
#define rep(i,a,b) for(int i=(int)(a);i<=(int)(b);i++)
#define per(i,a,b) for(int i=(int)(a);i>=(int)(b);i--)
#define mmm(a,b) memset(a,b,sizeof(a))
#define pb push_back
#define pill pair<int, int>
#define fi first
#define se second
void test(){cerr<<"\n";}
template<typename T,typename... Args>void test(T x,Args... args){cerr<<x<<" ";test(args...);}
const LL mod=1e9+7;
const int maxn=1e5+9;
const int inf=0x3f3f3f3f;
LL rd(){ LL ans=0; char last=' ',ch=getchar();
    while(!(ch>='0' && ch<='9'))last=ch,ch=getchar();
    while(ch>='0' && ch<='9')ans=ans*10+ch-'0',ch=getchar();
    if(last=='-')ans=-ans; return ans;
}
#define rd rd()
/*_________________________________________________________begin*/
const int N=909;
int match[N];
bool vis[N];
bool link[N][N];
int n,m;

int fin(int h){
    for(int i=1;i<=m;i++){
        if(vis[i]||!link[h][i])continue;
        vis[i]=1;
        if(match[i]==0||fin(match[i])){
            match[i]=h;return 1;
        }
    }
    return 0;
}

int X[900],Y[900];
int have[30][30];
int di[8][2]={1,2,-1,2,1,-2,-1,-2, 2,1,-2,1,2,-1,-2,-1};

int main(){
    n=rd,m=rd;
    rep(id,1,m){
        char x[4];
        scanf("%s",x);
        int i=x[0]-'A'+1;
        int j=x[1]-'0';
        if(strlen(x)==3){
            j=j*10+x[2]-'0';
        }
        have[i][j]=id;
        X[id]=i;
        Y[id]=j;
    }
    rep(i,1,m){
        rep(j,0,7){
            int x=X[i]+di[j][0];
            int y=Y[i]+di[j][1];
            if(x<1||x>n||y<1||y>n||!have[x][y])continue;
            link[i][have[x][y]]=1;
            link[have[x][y]][i]=1;
        }
    }
    int ans=0;
    rep(i,1,m){
        mmm(vis,0);
        if(fin(i))ans++;
    }
    printf("%d\n",ans/2);
}
发布了790 篇原创文章 · 获赞 348 · 访问量 22万+

猜你喜欢

转载自blog.csdn.net/jk_chen_acmer/article/details/105664957