Hdu1045
题目大意:
有一个n行n列的地图,其中 '.' 代表空地,可以建造炮台,'x' 代表墙,建造规则是:每两个炮台之间必须有一堵墙,否者这两个炮台就会互相摧毁。现在输入一张这样的地图,要你计算最多可以建造多少炮台?
解题思路:
根据地图,得到一张新的数字地图,这张数字地图的构建方法是:
大小和原地图一样,
计算原地图的每一个 ' . ' 所在行列中有多少个 ‘ . ’,并将新图对应位置赋为该值。计算方法是:在每一行或每一列中走到底,或者遇到 ' x ' 结束。(可以包括本身也可以不包括本身,这里用不包括本身的方法)。
将原图中所有的 ' x ' 所在位置赋值为 无穷大(一个达不到的数即可,这里可以为 8 ,因为,最大为4行4列,这里计算又不包括本身,所以一个点所在的行列所有格子加起来最大也就是 6)。
按照这个方法可以得到一个新的地图:
在新图中贪心求解:(数字越小,证明在该点建造炮台影响到的点越少,可以建造的炮台也就越多)
找出第一排最小的数,判断是否小于 8 否 : 则下一行 。 是 :计数,然后将该点自己及其所影响到的不能再建造炮台的点赋值为无穷大。再找出最小的数,重复上述步骤,直到这一行没有小于8的数。
下一行:重复第一行的步骤,直到走完所有行结束。
代码如下
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
int main (){
char **str;
int **a,n,i,j,k,x,y,t,sum=0;
while(scanf("%d",&n)&&n){
getchar();
str=(char **)malloc(sizeof(char *)*n);//动态申请二维字符数组 str[][]; 用于存放字符地图
for(i=0;i<n;i++){
str[i]=(char *)malloc(sizeof(char)*n);
}
a=(int **)malloc(sizeof(int *)*n);//动态申请二维整型数组 a[][]; 用于存放数字地图
for(i=0;i<n;i++){
a[i]=(int *)malloc(sizeof(int)*n);
}
for(i=0;i<n;i++){ //录入字符地图.
for(j=0;j<n;j++)
scanf("%c",&str[i][j]);
getchar();
}
for(i=0;i<n;i++){ //预处理过程,根据输入的字符地图形成新的利于操作的数字地图
for(j=0;j<n;j++){
t=0;
if(str[i][j]=='.'){
for(k=i-1;k>=0&&str[k][j]=='.';k--)//上
t++;
for(k=i+1;k<n&&str[k][j]=='.';k++)//下
t++;
for(k=j-1;k>=0&&str[i][k]=='.';k--)//左
t++;
for(k=j+1;k<n&&str[i][k]=='.';k++)//右
t++;
a[i][j]=t;
}
else
a[i][j]=8;
}
}
for(i=0;i<n;i++){
t=8;
for(j=0;j<n;j++){
if(a[i][j]<t){
t=a[i][j];
x=i;
y=j;
}
}
if(t!=8){
sum++;
i--;
a[x][y]=8;
for(k=x-1;k>=0&&a[k][y]!=8;k--) //上
a[k][y]=8;
for(k=x+1;k<n&&a[k][y]!=8;k++) //下
a[k][y]=8;
for(k=y-1;k>=0&&a[x][k]!=8;k--) //左
a[x][k]=8;
for(k=y+1;k<n&&a[x][k]!=8;k++) //右
a[x][k]=8;
}
}
printf("%d\n",sum);
sum=0;
}
return 0;
}
/* for(i=0;i<n;i++)
{
for(j=0;j<n;j++)
{
printf("%d",a[i][j]);
}
printf("\n");
}*/