您的位置:首页 > 大数据 > 人工智能

poj 2585 Window Pains zoj 2193

2013-10-14 08:02 309 查看
代码预处理了一下kinds(),表示覆盖方格(i, j)的窗口的集合,本题利用字符串的特性来储存的。

如果 !g[ screen[i][j] ][ cover[i][j][p] - '0' ] && ( screen[i][j] != cover[i][j][p] - '0' ),则<screen[i][j], cover[i][j][p] - '0'>存在一条有向边。

本题把每个窗口都抽象成一个顶点,如果窗口X覆盖窗口Y的话,则存在一条有向边<X, Y>,最后利用拓扑排序,查看是否存在环,如果存在,则死机。

测试数据1如图(a)测试数据如图(b);





点击打开 题目

#include <iostream>
#include <string>
#include <cstring>

using namespace std;

const int n = 4;
int screen

;//屏幕可分成n*n的
string cover

;//表示能覆盖点(i,j)的窗口集合
bool exist[10];//储存给定的图中,哪一类窗口存在
bool g[10][10];//建立邻接矩阵
string s;
int t;//窗口种类
int id[10];//某个窗口的入度

void kinds()//表示能覆盖点(i,j)的窗口集合
{
int i, j, k;
for(i = 0; i < n; ++i)
{
for(j = 0; j < n; ++j)
{
cover[i][j].erase();
}
}

for(k = 1; k <= 9; ++k)
{
i = (k - 1) / 3;
j = (k - 1) % 3;

cover[i][j] += (char)(k + '0');//第k个窗口的左上角位置,并且记录了覆盖方格(i, j)的窗口数目,利用字符串的特性来储存
cover[i][j+1] += (char)(k + '0');//第k个窗口右上角的位置
cover[i + 1][j] += (char)(k + '0');//第k个窗口左下角的位置
cover[i + 1][j + 1] += (char)(k + '0');//第k个窗口右下角的位置
}
}

void init()
{
int i, j, k;
memset(exist, false, sizeof(exist));
memset(g, false, sizeof(g));
memset(id, 0, sizeof(id));
t = 0;
for(i = 0; i < n; ++i)
{
for(j = 0; j < n; ++j)
{
cin>>k;
screen[i][j] = k;
if(!exist[k])
t++;//也就是屏幕截图中存在窗口的种类
exist[k] = true;
}
}
}

void build_map()//建图
{
int i, j, p;
for(i = 0; i < n; ++i)
{
for(j = 0; j < n; ++j)
{
int m = cover[i][j].length();//覆盖方格(i, j)的数目;
for(p = 0; p < m; ++p)
{//把每个窗口抽象成一个顶点,如果顶点X覆盖顶点Y,则存在一条有向边<X,Y>
if( !g[ screen[i][j] ][ cover[i][j][p] - '0' ] && ( screen[i][j] != cover[i][j][p] - '0' ) )
{
g[ screen[i][j] ][ cover[i][j][p] - '0' ] = true;
id[ cover[i][j][p] - '0' ]++;
}
}
}
}
}

bool Check_circle()//查看图中是否存在环
{
int i, j, k;
for(k = 0; k < t; ++k)
{
i = 1;
//记录出现在屏幕截图中,并且定点的入度不为零的窗口个数,其实也等价于查找屏幕截图中入度为零的窗口;
//如果某个窗口没有出现在屏幕截图中,则该顶点的入度一定不等于零
while( !exist[i] || (i <= 9 && id[i] > 0))
i++;
if(i > 9)
return false;
exist[i] = false;
for(j = 1; j <= 9; ++j)
{
if( exist[j] && g[i][j] )
id[j]--;
}
}
return true;
}
int main()
{
kinds();
while(cin>>s)
{
if(s == "ENDOFINPUT")
break;
init();
build_map();
if( Check_circle() )
cout<<"THESE WINDOWS ARE CLEAN"<<endl;
else
cout<<"THESE WINDOWS ARE BROKEN"<<endl;
cin>>s;
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: