hdu2819 Swap (二分图匹配+匹配结果的利用)

问题描述

给定一个N*N矩阵,每个元素都等于0或1。您可以交换任意两行或任意两列。你能找到一种方法使所有对角元素都等于1吗?

输入

输入中有几个测试用例。每个测试用例的第一行是一个整数N (1 <= N <= 100)。然后是N行,每一行包含N个数字(0或1),按空间分开,表示N*N矩阵。

输出

对于每个测试用例,第一行包含的数量M,然后M行,其格式是“R a b”或“C a b”,表明交换行a和行b,或交换列a和列b。(1 < = a、b < = N)。任何正确的答案将被接受,但应该超过1000。
如果不可能使所有对角元素都等于1,那么只输出一个包含“-1”的元素。

分析:

先求最大匹配,如果最大匹配不等于n说明不可能满足条件(类似‘摆放象棋的车’那题)。
我以为匹配就用在判断上,接下来的交换我真的是一行一行换的。。
就是从第一个开始,如果对角线上的不等于1,向下搜索,搜到交换完能变成1的就一整行交换。
但是这样无限wa,(后来想了想知道是为什么了)

正解是利用匹配结果,不仅能保证交换次数而且肯定正确。
看别人代码学到的(不好解释,直接看代码思考)。

这题加深了我对匹配的理解,当场记录!

code:

#include<iostream>
#include<cstdio>
#include<cstring>
#include<vector>
#include<cmath>
typedef long long ll;
const int inf=0x3f3f3f3f;
const int inn=0x80808080;
using namespace std;
const int maxm=105;
int g[maxm][maxm];
int mark[maxm];
int now[maxm];
int n;
int dfs(int x){
    for(int i=1;i<=n;i++){
        if(g[x][i]&&!mark[i]){
            mark[i]=1;
            if(!now[i]||dfs(now[i])){
                now[i]=x;
                return 1;
            }
        }
    }
    return 0;
}
int main(){
    while(cin>>n){
        for(int i=1;i<=n;i++){
            for(int j=1;j<=n;j++){
                cin>>g[i][j];
            }
        }
        int ans=0;
        memset(now,0,sizeof now);
        for(int i=1;i<=n;i++){
            memset(mark,0,sizeof mark);
            ans+=dfs(i);
        }
        if(ans!=n){
            cout<<-1<<endl;
            continue;
        }
        vector<int>aa;
        vector<int>bb;
        for(int i=1;i<=n;i++){
            if(now[i]!=i){
                for(int j=i+1;j<=n;j++){
                    if(now[j]==i){
                        aa.push_back(i);//注意这里交换的是列,所以是C a b
                        bb.push_back(j);//
                        swap(now[i],now[j]);
                        break;
                    }
                }
            }
        }
        printf("%d\n",aa.size());
        for(int i=0;i<(int)aa.size();i++){
            printf("C %d %d\n",aa[i],bb[i]);
        }
    }
    return 0;
}


猜你喜欢

转载自blog.csdn.net/weixin_44178736/article/details/92800545
今日推荐