POJ 3041 Asteroids

题目链接:

题目大意:

  • 一个NxN矩阵,有一些障碍在矩阵中;
  • 消除障碍,一次可以消除一行或者一列;
  • 问最小次数

解题思路:

  • 可以将每一行,每一列看做一个端点;
  • 障碍看做两个端点之间的边, 那么NxN矩阵就转化为了一个无向图。
  • 最后只求最小点覆盖,即为答案
  • 最小点覆盖 = 二分图的最大匹配, 证明:http://www.matrix67.com/blog/archives/116
#include<iostream>
#include<string.h>
#include<vector>
#include<string>
#include<algorithm>
using namespace std;

const int N = 507;

vector<vector<bool>>vec(N,vector<bool>(N, false));
bool visited[N];
int match[N];
int n, k;

bool dfs(int u)
{
    for(int v=1; v<=n; ++ v)
    {
        if(vec[u][v] && visited[v] == false)
        {
            visited[v] = true;
            if(match[v] == -1 || dfs(match[v]))
            {
                match[v] = u;
                return true;
            }
        }
    }
    return false;
}


int main()
{
    ios::sync_with_stdio(false);

    cin >> n >> k;

    for(int i=0; i<k; ++i)
    {
        int r, c;
        cin >> r >> c;
        vec[r][c] = true;
    }

    memset(match, -1, sizeof(match));
    int ans = 0;
    for(int i=1; i<=n; ++ i)
    {
        memset(visited,false, sizeof(visited));
        if(dfs(i))
            ans ++;
    }
    cout << ans << endl;
    return 0;
}
原文地址:https://www.cnblogs.com/aiterator/p/6563773.html