现在炸弹不是想放在那里就能放在那里的了,必须由小人能够走到的地方才能放置炸弹。比如下面这个例子小人默认站在(3,3)这个位置。请问放在何处最多可以消灭多个敌人。
解释:上面解炸弹人的方法有可能小人并不能走到那里去,也就不能放置炸弹。我们可以通过深度优先和广度优先来进行搜索,确保该点小人可以到达,再在可到达的点周围确定可以消灭敌人的数目。
dfs:先更新最大值,再循环
#include <stdio.h>
int book[51][51] = {0};
char a[51][51];//记录地图
int max,n,m,mx,my;
int getsum(int i,int j)
{
int sum,x,y;
sum = 0;
x = i;
y = j;
while(a[x][y]!='#')//不为墙 向上检查
{
if(a[x][y]=='G')
{
sum++;
}
x--;
}
x = i;
y = j;
while(a[x][y]!='#')//不为墙 向下检查
{
if(a[x][y]=='G')
{
sum++;
}
x++;
}
x = i;
y = j;
while(a[x][y]!='#')//不为墙 向左检查
{
if(a[x][y]=='G')
{
sum++;
}
y--;
}
x = i;
y = j;
while(a[x][y]!='#')//不为墙 向右检查
{
if(a[x][y]=='G')
{
sum++;
}
y++;
}
return sum;
}
void dfs(int x,int y)
{
int tx,ty,k,sum;
int next[4][2]={{0,1},{1,0},{0,-1},{-1,0}};//搜索的方向,右,下,左,上
sum = getsum(x,y);//以该点为中心,向四个方向寻找可以消灭敌人的总数
if(sum>max)//更新最大值并且记录横纵坐标
{
max = sum;
mx = x;
my = y;
}
for(k = 0;k <= 3;k++)
{
tx = x+next[k][0];
ty = y+next[k][1];
if(tx<0||tx>n-1||ty<0||ty>m-1)//边界
{
continue;
}
if(a[tx][ty]=='.'&&book[tx][ty]==0)//判断是否为平地或曾经走过
{
book[tx][ty] = 1;
dfs(tx,ty);
}
}
return;
}
int main()
{
int i,x,y;
scanf("%d%d%d%d",&n,&m,&x,&y);//读入行和列,起始坐标
for(i = 0;i < n;i++)//读入地图
{
scanf("%s",a[i]);
}
book[x][y]=1;
max = getsum(x,y);
mx = x;
my = y;
dfs(x,y);
printf("%d",max);
return 0;
}
bfs:先循环,再更新最大值
#include <stdio.h>
struct node
{
int x;//横坐标
int y;//纵坐标
};
char a[51][51];//记录地图
int getsum(int i,int j)
{
int sum,x,y;
sum = 0;
x = i;
y = j;
while(a[x][y]!='#')//不为墙 向上检查
{
if(a[x][y]=='G')
{
sum++;
}
x--;
}
x = i;
y = j;
while(a[x][y]!='#')//不为墙 向下检查
{
if(a[x][y]=='G')
{
sum++;
}
x++;
}
x = i;
y = j;
while(a[x][y]!='#')//不为墙 向左检查
{
if(a[x][y]=='G')
{
sum++;
}
y--;
}
x = i;
y = j;
while(a[x][y]!='#')//不为墙 向右检查
{
if(a[x][y]=='G')
{
sum++;
}
y++;
}
return sum;
}
int main()
{
struct node que[2501];
int book[51][51] = {0};//定义一个标记数组并全部初始化为0
int next[4][2]={{0,1},{1,0},{0,-1},{-1,0}};//搜索的方向,右,下,左,上
int i,j,sum,k,mx,my,x,y,n,m,head,tail,max = 0,tx,ty;
head = 1;
tail = 1;
scanf("%d%d%d%d",&n,&m,&x,&y);//读入行和列,起始坐标
for(i = 0;i < n;i++)//读入地图
{
scanf("%s",a[i]);
}
que[tail].x = x;//初始化
que[tail].y = y;
book[x][y] = 1;
tail++;
max = getsum(x,y);//记录初始点的信息
mx = x;
my = y;
while(head<tail)
{
for(k = 0;k <= 3;k++)
{
tx = que[head].x+next[k][0];
ty = que[head].y+next[k][1];
if(tx<0||tx>n-1||ty<0||ty>m-1)//边界
{
continue;
}
if(a[tx][ty]=='.'&&book[tx][ty]==0)//判断是否为平地或曾经走过
{
book[tx][ty] = 1;
que[tail].x = tx;
que[tail].y = ty;
tail++;
sum = getsum(tx,ty);//以该点为中心,向四个方向寻找可以消灭敌人的总数
if(sum>max)//更新最大值并且记录横纵坐标
{
max = sum;
mx = tx;
my = ty;
}
}
}
head++;
}
// printf("将炸弹放置在(%d,%d)处,最大可消灭敌人数为:%d\n",mx,my,max);
printf("%d",max);
return 0;
}