题目太长了。。看懂了也没啥难得。。这里就不翻译了。。大概意思就是把一个长宽为2的幂次的图像化为一个四分树,并且标出到黑色像素块的路径,以一个十进制整数表示。怎么表示题目里有图示,比较容易理解。
图像化树:用矩形的左上角和右下角两个点的坐标来确定矩形的位置,扫描整个矩形块,如果不是单色的就递归扫描这个矩形的四个部分。是单色的就记录下路径加入ans数组。
树化图像:仍然是用对角线上的两个点确定矩形的位置。十进制数每次对5取余就能得到当前在哪个矩形块中。然后把代表路径的数除以5,重复之前的取余访问矩形块的步骤,循环直到路径为0。然后把当前所在的矩形块染黑就行。
AC代码如下。。。有点长。。不过思路应该很清楚的。对了。坑爹的地方在于输出格式。每两个output之间应该用空行隔开。。而且最后一次的输出不能有空行。。
#include <cstdio>
#include <algorithm>
#include <cstring>
#include <vector>
using namespace std;
char G[65][65];
char G2[65][65];
vector<int> ans;
int to_decimal(int a)
{
int b=0,base=1;
while(a)
{
b+=base*(a%10);
base*=5;
a/=10;
}
return b;
}
void step_in(int x1,int y1,int x2,int y2,int path)
{
if(path==0)
{
for(int i=y1;i<=y2;i++)
{
for(int j=x1;j<=x2;j++)
{
G[i][j]='*';
}
}
return;
}
else
{
int pos=path%5;
int new_x1=x1,new_x2=x2,new_y1=y1,new_y2=y2;
switch(pos)
{
case(1):
{
new_x2=(x2+x1-1)/2;
new_y2=(y2+y1-1)/2;
break;
}
case(2):
{
new_x1=(x1+x2+1)/2;
new_y2=(y2+y1-1)/2;
break;
}
case(3):
{
new_y1=(y2+y1+1)/2;
new_x2=(x2+x1-1)/2;
break;
}
case(4):
{
new_x1=(x2+x1+1)/2;
new_y1=(y2+y1+1)/2;
break;
}
}
step_in(new_x1,new_y1,new_x2,new_y2,path/5);
}
}
void divide(int x1,int y1,int x2,int y2,int pre_path,int pos,int t)
{
int has_black=0,has_white=0,ok=0;
for(int i=y1;i<=y2;i++)
{
for(int j=x1;j<=x2;j++)
{
if(G2[i][j]=='1')
has_black=1;
else
has_white=1;
if(has_black&&has_white)
{
ok=1;
break;
}
}
if(ok==1)
break;
}
for(int i=2;i<=t;i++)
pos*=10;
pre_path=pos+pre_path;
if(has_white==0&&has_black==1)
{
ans.push_back(pre_path);
return;
}
else if(has_white==1&&has_black==0)
return;
else
{
divide(x1,y1,(x2+x1-1)/2,(y2+y1-1)/2,pre_path,1,t+1);
divide((x2+x1+1)/2,y1,x2,(y2+y1-1)/2,pre_path,2,t+1);
divide(x1,(y2+y1+1)/2,(x2+x1-1)/2,y2,pre_path,3,t+1);
divide((x2+x1+1)/2,(y2+y1+1)/2,x2,y2,pre_path,4,t+1);
}
}
int main()
{
int t,cnt=0,first=1;
while(scanf("%d", &t)&&t!=0)
{
if(first)
{
first=0;
}
else
{
printf("\n");
}
cnt++;
if(t>0)
{
ans.clear();
for(int i=1;i<=t;i++)
{
scanf("%s", &G2[i][1]);
}
divide(1,1,t,t,0,0,0);
sort(ans.begin(),ans.end());
int count=0;
printf("Image %d\n", cnt);
for(int i=0;i<ans.size();i++)
{
count++;
if(i%12==0)
printf("%d", to_decimal(ans[i]));
else
printf(" %d", to_decimal(ans[i]));
if(count%12==0||i==ans.size()-1)
printf("\n");
}
printf("Total number of black nodes = %d\n",ans.size());
}
else if(t<0)
{
for(int i=1;i<=(-t);i++)
{
for(int j=1;j<=(-t);j++)
G[i][j]='.';
}
int n;
while(scanf("%d", &n)&&n!=-1)
{
if(n==0)
{
for(int i=1;i<=(-t);i++)
{
for(int j=1;j<=(-t);j++)
G[i][j]='*';
}
}
else
{
step_in(1,1,(-t),(-t),n);
}
}
printf("Image %d\n", cnt);
for(int i=1;i<=(-t);i++)
{
for(int j=1;j<=(-t);j++)
printf("%c", G[i][j]);
printf("\n");
}
}
}
return 0;
}