您的位置:首页 > 其它

hdu 1507 Uncle Tom's Inherited Land* 【黑白染色+奇偶匹配(1X2的矩形覆盖)】

2013-08-28 20:30 330 查看
题目:Uncle Tom's Inherited Land*

题意:有一个矩阵,被分成很多小方格。有些小方格有障碍,问最多能在矩阵中

放多少1*2的矩形。

分析:黑白染色+奇偶匹配。

把格子染成国际象棋棋盘那种黑白相间。这样就能再矩阵中找出两个不相交的

点集进行二分匹配。把坐标(i,j)按照(i+j)的奇偶分类。每个格子只能与周围四个

不同颜色的匹配。这里BFS一下。然后二分匹配。

代码:

#include<cstdio>
#include<iostream>
#include<cstring>
using namespace std;

int g[105][105];
int match[105][105];
int vis[105][105];
int dx[4]={-1,1,0,0};
int dy[4]={0,0,-1,1};
int n,m;

int f(int i,int j)
{
return (i-1)*m+j-1;
}
bool dfs(int u)
{
int x=u/m+1,y=u%m+1;
for(int i=0;i<4;i++)
{
int xx=x+dx[i];
int yy=y+dy[i];
if(vis[xx][yy] || g[xx][yy])
continue;
vis[xx][yy]=1;
if(match[xx][yy]==-1 || dfs(match[xx][yy]))
{
match[xx][yy]=u;
return true;
}
}
return false;
}
int get_max_match()
{
int i,j;
int cnt=0;
for(i=1;i<=n;i++)
{
for(j=1;j<=m;j++)
{
if((i+j)%2 && g[i][j]==0)
{
memset(vis,0,sizeof(vis));
if(dfs(f(i,j)))
cnt++;
}
}
}
return cnt;
}
int main()
{
int k,i,j,a,b,ans;
while(scanf("%d%d",&n,&m)&&n&&m)
{
scanf("%d",&k);
memset(g,0,sizeof(g));
memset(match,-1,sizeof(match));
for(i=1;i<=k;i++)
{
scanf("%d%d",&a,&b);
g[a]=1;
}
for(i=0;i<=n+1;i++)  //边界处理成不能走
{                    //便于bfs时判断
g[i][m+1]=1;
g[i][0]=1;
}
for(i=0;i<=m+1;i++)
{
g[0][i]=1;
g[n+1][i]=1;
}
ans=get_max_match();
printf("%d\n",ans);
for(i=1;i<=n;i++)
{
for(j=1;j<=m;j++)
{
if(match[i][j]!=-1)
printf("(%d,%d)--(%d,%d)\n",i,j,match[i][j]/m+1,match[i][j]%m+1);
}
}
}
return 0;
}


感想:

[b]今天写的程序全部都WA了。。。终于有个AC了。。。。我真是涕泗横流啊。。。。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: