문제 링크 : https://www.acmicpc.net/problem/14503
이 문제는 문제의 조건대로 하나하나 구현해나가면 쉽게 풀 수 있습니다.
문제의 편리한 점은 외곽이 모두 벽이기 때문에 배열 밖으로 나가는 부분에 대해서 벨리데이션을 진행할 필요 없이 벽 부분의 check 배열을 미리 true로 설정해놓으면 check 배열 하나로 벨리데이션이 가능합니다.
다음은 코드입니다.
import java.util.*;
import java.io.*;
public class Main{
static int N,M,r,c,d;
static int[] dx = {0,1,0,-1};
static int[] dy = {-1,0,1,0};
static int res = 0;
static int[][] req = new int[51][51];
static boolean[][] check = new boolean[51][51];
static void stepOne(int y, int x){
// 현재 위치 청소
check[y][x] = true;
res++;
}
static void stepTwo(int y, int x, int dir){
for(int i=0;i<4;i++){
// 1. 왼쪽 방향에 아직 청소하지 않은 공간이 존재한다면, 그 방향으로 회전한 다음 한 칸을 전진하고 1번부터 진행한다.
// 인덱스를 1씩 빼고 만약에 북쪽이면 3으로 치환
int newDir = dir-1;
if(newDir<0) newDir=3;
int ny = y + dy[newDir];
int nx = x + dx[newDir];
if(!check[ny][nx]) {
stepOne(ny,nx);
stepTwo(ny,nx,newDir);
return;
}
else dir = newDir;
// 2. 왼쪽 방향에 청소할 공간이 없다면, 그 방향으로 회전하고 2번으로 돌아간다.
}
// 3. 네 방향 모두 청소가 이미 되어있거나 벽인 경우에는, 바라보는 방향을 유지한 채로 한 칸 후진을 하고 2번으로 돌아간다.
int ny = y - dy[dir];
int nx = x - dx[dir];
if(req[ny][nx]==0) stepTwo(ny,nx,dir);
// 4. 네 방향 모두 청소가 이미 되어있거나 벽이면서, 뒤쪽 방향이 벽이라 후진도 할 수 없는 경우에는 작동을 멈춘다.
else return;
}
public static void main(String[] args) throws Exception{
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st = new StringTokenizer(br.readLine());
N = Integer.parseInt(st.nextToken());
M = Integer.parseInt(st.nextToken());
st = new StringTokenizer(br.readLine());
r = Integer.parseInt(st.nextToken());
c = Integer.parseInt(st.nextToken());
d = Integer.parseInt(st.nextToken());
for(int i=0;i<N;i++){
st = new StringTokenizer(br.readLine());
for(int j=0;j<M;j++){
req[i][j] = Integer.parseInt(st.nextToken());
if(req[i][j]==1) check[i][j] = true;
}
}
stepOne(r,c);
stepTwo(r,c,d);
System.out.println(res);
}
}