题目描述
一个矩形的房间铺着红色或者黑色的方砖。一个人站在红砖上不能移动,在黑砖上可以沿着上、下、左、右4个方向移动到相邻的方砖。请编写一个程序,计算从起点出发可以到达的黑色方砖的数量(包括起点在内)。
起点是@,要求:遍历所有黑砖。
输入
输出从起点出发可以到达的黑砖的数量(包括起点在内)。
输出
15
c++ bfs
#include<bits/stdc++.h>
using namespace std;
int n,m,ans;
char a[25][25];
int d[4][2]= {{-1,0},{1,0},{0,-1},{0,1}};
struct no
{
int x;
int y;
};
void bfs(int dx,int dy)//广搜遍历
{
ans=1;
queue<no>q;
no str,ne;
str.x=dx;
str.y=dy;
q.push(str);
while(!q.empty())
{
str=q.front();
q.pop();
for(int i=0; i<4; i++)
{
ne.x=str.x+d[i][0];
ne.y=str.y+d[i][1];
if(ne.x>=0&&ne.x<n&&ne.y>=0&&ne.y<m&&a[ne.x][ne.y]=='.')
{
a[ne.x][ne.y]='#';
ans++;
q.push(ne);
}
}
}
}
int main()
{
int dx,dy;
while(cin>>n>>m)
{
if(n==0&&m==0)
break;
for(int j=0; j<m; j++)
{
for(int i=0; i<n; i++)
{
cin>>a[i][j];
if(a[i][j]=='@')
{
dx=i;
dy=j;
}
}
}
ans=0;
bfs(dx,dy);
cout<<ans<<endl;
}
return 0;
}
DFS
import java.util.Scanner;
public class Main{
static int w = 0;//每个测试房间的宽度
static int h = 0;//每个测试房间的高度
static char room[][] = new char[21][21];//房间
static int sum = 1;//计算可到达的方格
public static void main(String args[]){
Scanner sc = new Scanner(System.in);
while(sc.hasNext()){
w = sc.nextInt();
h = sc.nextInt();
if(w == 0 && h == 0)break;
String a = "";
for(int i = 0;i < h;i++){
a = sc.next();
room[i] = a.toCharArray();
}
//遍历房间寻找起点
int x = 0,y = 0;
for(int i = 0;i < h;i++){
for(int j = 0;j < w;j++){
if(room[i][j] == '@'){
x = j;
y = i;
}
}
}
dfs(x,y);
System.out.println(sum);
sum = 1;
}
}
static void dfs(int x, int y){
if( y >= 0 && x >= 0 && y < h && x < w){
if(room[y][x] == '#')return;//不可前进时停止
if(room[y][x] == '.')
++sum;//计数
}
else return;//到达房间边缘时停止
room[y][x] = '#';//将走过的地板变为不可行走
//继续前进
dfs(x-1,y);
dfs(x+1,y);
dfs(x,y-1);
dfs(x,y+1);
}
}
BFS
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.Queue;
import java.util.Scanner;
class Point{
public int x;
public int y;
}
public class Main {
static int ans=0;//数量初始化为0
static int[][] dir={{0,1},{0,-1},{-1,0},{1,0}};//右左上下四个方向
public static void main(String[] args) {
// TODO Auto-generated method stub
Scanner in=new Scanner(System.in);
int n=in.nextInt();//列数
int m=in.nextInt();//行数
Queue<Point> q=new LinkedList<Point>();//利用队列实现bfs
while(m!=0&&n!=0){//不为0时读入
char gra[][]=new char[m][n];//存迷宫
boolean vis[][]=new boolean[m][n];//标记是否访问
Point p=new Point();//表示坐标点位置
for(int i=0;i<m;i++){
String s=in.next();
for(int j=0;j<s.length();j++){
gra[i][j]=s.charAt(j);
if(gra[i][j]=='@'){ //找到@起始的位置
p.x=i;//x,y为搜索起点
p.y=j;
}
}
}
bfs(gra,vis,p,m,n,q);//调用
System.out.println(ans+1);//输出答案
ans=0;//恢复为0,为下一组做准备
q.clear();//清空队列
n=in.nextInt();//读入列
m=in.nextInt();//读入行
}
}
private static void bfs(char[][] gra, boolean vis[][],Point p, int m, int n,Queue q) {
// TODO Auto-generated method stub
vis[p.x][p.y]=true;//将起始点标记为已访问
q.add(p);//将起始点放入队列中
while(!q.isEmpty())//队列不为空时
{
Point qq=(Point) q.remove();//取出第一个元素
for(int i=0;i<4;i++)//枚举该点附近所有能到达的点
{
Point pp=new Point();
pp.x=qq.x+dir[i][0];
pp.y=qq.y+dir[i][1];
if((!(pp.x<0||pp.x>=m||pp.y<0||pp.y>=n))&&vis[pp.x][pp.y]==false&&gra[pp.x][pp.y]=='.')//如果点合法
{
vis[pp.x][pp.y]=true;//标记已访问
q.add(pp);//将该点加入队列中
ans++;//可达点数目+1
}
}
}}
}