(最小路径覆盖) poj 2446

E - Chessboard

Time Limit:2000MS     Memory Limit:65536KB     64bit IO Format:%I64d & %I64u

Submit Status Practice POJ 2446

Description

Alice and Bob often play games on chessboard. One day, Alice draws a board with size M * N. She wants Bob to use a lot of cards with size 1 * 2 to cover the board. However, she thinks it too easy to bob, so she makes some holes on the board (as shown in the figure below). 

We call a grid, which doesn’t contain a hole, a normal grid. Bob has to follow the rules below: 
1. Any normal grid should be covered with exactly one card. 
2. One card should cover exactly 2 normal adjacent grids.

Some examples are given in the figures below: 

A VALID solution.

An invalid solution, because the hole of red color is covered with a card.

An invalid solution, because there exists a grid, which is not covered.
Your task is to help Bob to decide whether or not the chessboard can be covered according to the rules above.

Input

There are 3 integers in the first line: m, n, k (0 < m, n <= 32, 0 <= K < m * n), the number of rows, column and holes. In the next k lines, there is a pair of integers (x, y) in each line, which represents a hole in the y-th row, the x-th column.

Output

If the board can be covered, output "YES". Otherwise, output "NO".

Sample Input

4 3 2
2 1
3 3

Sample Output

YES

Hint


A possible solution for the sample input.

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<cstdlib>
#include<string>
#include<queue>
#include<vector>
#include<stack>
using namespace std;
int mp[1230][1230],link[1230],mark[1230],g[35][35],ans,opt[35][35];
int n,m,k,temp;
bool dfs(int x)
{
    for(int i=1;i<=temp;i++)
    {
        if(mark[i]==-1&&mp[x][i])
        {
            mark[i]=1;
            if(link[i]==-1||dfs(link[i]))
            {
                link[i]=x;
                return true;
            }
        }
    }
    return false;
}
int main()
{
    int x,y;
    while(scanf("%d%d%d",&n,&m,&k)!=EOF)
    {
        temp=0;
        ans=0;
        memset(link,-1,sizeof(link));
        memset(g,0,sizeof(g));
        memset(opt,0,sizeof(opt));
        for(int i=1;i<=k;i++)
        {
            scanf("%d%d",&y,&x);
            opt[x][y]=1;
        }
        for(int i=1;i<=n;i++)
        {
            for(int j=1;j<=m;j++)
            {
                if(!opt[i][j])
                {
                    g[i][j]=++temp;
                }
            }
        }
        memset(mp,0,sizeof(mp));
        for(int i=1;i<=n;i++)
        {
            for(int j=1;j<=m;j++)
            {
                if(g[i][j]!=0)
                {
                    if(i>1&&g[i-1][j]!=0)
                        mp[g[i][j]][g[i-1][j]]=1;
                    if(i<n&&g[i+1][j]!=0)
                        mp[g[i][j]][g[i+1][j]]=1;
                    if(j>1&&g[i][j-1]!=0)
                        mp[g[i][j]][g[i][j-1]]=1;
                    if(j<m&&g[i][j+1]!=0)
                        mp[g[i][j]][g[i][j+1]]=1;
                }
            }
        }
        for(int i=1;i<=temp;i++)
        {
            memset(mark,-1,sizeof(mark));
            if(dfs(i))
                ans++;
        }
        if(ans==temp)
            printf("YES\n");
        else
            printf("NO\n");
    }
    return 0;
}

  

时间: 2024-08-10 21:45:24

(最小路径覆盖) poj 2446的相关文章

(最小路径覆盖) poj 1422

Air Raid Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 6908   Accepted: 4114 Description Consider a town where all the streets are one-way and each street leads from one intersection to another. It is also known that starting from an i

POJ - 3020 Antenna Placement 二分图 最小路径覆盖

题目大意:有n个城市,要在这n个城市上建立无线电站,每个无线电站只能覆盖2个相邻的城市,问至少需要建多少个无线电站 解题思路:英语题目好坑,看了半天.. 这题和POJ - 2446 Chessboard类似 可以将所有城市分成两个点集,那么之间的连线就代表无线电站的覆盖关系了. 因为所有城市都要覆盖到,所以根据关系,求出最小路径覆盖就能覆盖所有城市了 #include<cstdio> #include<algorithm> #include<cstring> #incl

POJ 3020 Antenna Placement ,二分图的最小路径覆盖

题目大意: 一个矩形中,有N个城市'*',现在这n个城市都要覆盖无线,若放置一个基站,那么它至多可以覆盖相邻的两个城市. 问至少放置多少个基站才能使得所有的城市都覆盖无线? 无向二分图的最小路径覆盖 = 顶点数 –  最大二分匹配数/2 路径覆盖就是在图中找一些路径,使之覆盖了图中的所有顶点,且任何一个顶点有且只有一条路径与之关联: #include<cstdio> #include<cstring> #include<vector> #include<algor

POJ 2594 Treasure Exploration(最小路径覆盖变形)

POJ 2594 Treasure Exploration 题目链接 题意:有向无环图,求最少多少条路径能够覆盖整个图,点能够反复走 思路:和普通的最小路径覆盖不同的是,点能够反复走,那么事实上仅仅要在多一步.利用floyd求出传递闭包.然后依据这个新的图去做最小路径覆盖就可以 代码: #include <cstdio> #include <cstring> #include <vector> #include <algorithm> using names

POJ 2060 Taxi Cab Scheme【最小路径覆盖】

T - Taxi Cab Scheme Time Limit:1000MS     Memory Limit:30000KB     64bit IO Format:%I64d & %I64u Submit Status Practice POJ 2060 Appoint description:  System Crawler  (2014-08-22) Description Running a taxi station is not all that simple. Apart from

POJ 3020 Antenna Placement(二分图建图训练 + 最小路径覆盖)

题目链接:http://poj.org/problem?id=3020 Antenna Placement Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 6692   Accepted: 3325 Description The Global Aerial Research Centre has been allotted the task of building the fifth generation of mobi

POJ 3020:Antenna Placement(无向二分图的最小路径覆盖)

Antenna Placement Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 6334   Accepted: 3125 Description The Global Aerial Research Centre has been allotted the task of building the fifth generation of mobile phone nets in Sweden. The most st

POJ 3216 最小路径覆盖+floyd

Repairing Company Time Limit: 1000MS   Memory Limit: 131072K Total Submissions: 6646   Accepted: 1788 Description Lily runs a repairing company that services the Q blocks in the city. One day the company receives M repair tasks, the ith of which occu

POJ 3020 (二分图+最小路径覆盖)

题目链接:http://poj.org/problem?id=3020 题目大意:读入一张地图.其中地图中圈圈代表可以布置卫星的空地.*号代表要覆盖的建筑物.一个卫星的覆盖范围是其周围上下左右四个点.问最少需要几个卫星才能覆盖所有建筑物. 解题思路: 有点类似POJ 1328的覆盖题,不过那题比较简单可以贪心.这题你可以YY试试. 覆盖问题其实可以用图论解决.这题就属于最小路径覆盖,手动由一个点出发连一些路径,这样Hungry就能求出最少需要多少这样的中心点,就可以达成目标了. 本题最大的疑问是

POJ 1422 DAG最小路径覆盖

求无向图中能覆盖每个点的最小覆盖数 单独的点也算一条路径 这个还是可以扯到最大匹配数来,原因跟上面的最大独立集一样,如果某个二分图(注意不是DAG上的)的边是最大匹配边,那说明只要取两个端点只要一条边即可. 故最小覆盖数还是 顶点数-最大匹配数 根据DAG建图的时候,就是DAG有边就给对应的端点建边 #include <iostream> #include <cstdio> #include <cstring> using namespace std; int d[15