티스토리 뷰
https://www.acmicpc.net/problem/20420

문제
민규는 25년간의 외로운 수련 끝에 드디어 마법사가 되었다. 마법사가 된 민규에게는 꿈이 있었으니.. 마법같이 멋진 테마파크를 짓는 것이었다! 민규는 테마파크의 첫 상품으로 "화살표 미로"를 공개했다.
화살표 미로는 평범한 미로와 다른 점이 많다. 이 미로는 R×C 개의 방으로 이루어져 있다. 모든 방이 서로 이동할 수 없도록 사방이 벽으로 막혀있고, 각 방마다 완전히 다른 테마의 화려한 볼거리로 꾸며져 있다.

사방이 벽으로 막혀있다면 어떻게 다른 방으로 이동할 수 있을까? 민규는 각 방마다 특별한 마법진을 그려 각 마법진에 그려져 있는 화살표의 방향으로 한 칸 순간이동 할 수 있도록 설계했다! 미로의 가장 바깥벽은 마그마로 둘러싸여 있어, 미로를 둘러싸고 있는 가장 바깥벽을 넘어가 미로 자체를 탈출하지는 못한다.
화살표 미로를 이용하는 고객들은 미로의 가장 왼쪽 위인 (1,1)방에 있는 입구에서 시작해 다양한 방들을 경험하고, 미로의 가장 오른쪽 아래인 (R,C)방에 있는 출구를 끝으로 미로를 마쳐야한다. 만약 그러지 못한다면 영원히 화살표 미로를 헤매게 될 것이다! 당연하지만, 처음 민규가 그려둔 마법진의 화살표 방향에 따라 출구에 가지 못할 수 있다.
민규는 화살표 미로를 사람들이 안전하게 즐길 수 있도록 화살표 미로의 입구에서 특별한 주문서를 팔기로 했다. 주문서는 화살표를 반시계 방향으로 회전시키는 'L 주문서'와 시계 방향으로 회전시키는 'R 주문서' 두 종류가 있다. 이 주문서를 사용하면 해당 방향으로 화살표가 90도 회전하게 된다. 몇 장의 주문서를 한 마법진에 연달아 사용해 180도, 270도 회전하도록 만들 수도 있다. 민규는 수익을 극대화 하기 위해 L 주문서와 R 주문서를 각각 한 장씩 묶어 한 세트로만 팔고 있다.
화살표 미로를 이용하는 고객들은 미로에 입장하고서야 지도를 받을 수 있어, 화살표 미로에서 영원히 헤매지 않으려면 울며 겨자 먹기로 대량의 주문서 세트를 구매해야만 했다. 화살표 미로를 즐겨 이용하던 민규의 친구 준서도 이런 불편을 겪고 있었다.
준서 : 아니, 적어도 지금 가진 걸론 충분한지 아닌지는 말해 줘야 하는 거 아니야 ??
준서의 불평에 지친 민규는 특별히 준서에게만, 준서가 가지고 있는 주문서 세트로 출구까지 가는 데 충분하냐는 질문에 단 한 번 "Yes" 또는 "No"로 대답해주기로 했다. 정확하게 답해주는 것은 민규에게 매우 어려운 일이기 때문에, 민규는 당신에게 질문에 대신 답해주는 프로그램을 의뢰했다.
유형 : BFS
접근 방식
- 방문 배열을 4차원으로 선언한다. x,y좌표와 왼쪽 회전 주문서 , 오른쪽 회전 주문서를 나타내도록 한다.
전체 코드
import java.util.*;
import java.io.*;
public class Main {
static int n,m,k;
// R D L U
static int[] dx = {0,1,0,-1};
static int[] dy = {1,0,-1,0};
static int[][] board;
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());
k = Integer.parseInt(st.nextToken());
board = new int[n+1][m+1];
for(int i = 1 ; i <= n ; i++){
char[] arr = br.readLine().toCharArray();
for(int j = 1 ; j <= m ; j++){
if(arr[j-1] == 'R'){
board[i][j] = 0;
}else if(arr[j-1] == 'D'){
board[i][j] = 1;
}else if(arr[j-1] == 'L'){
board[i][j] = 2;
}else{
board[i][j] = 3;
}
}
}
bfs();
br.close();
}
static void bfs(){
String result = "No";
int[][][][] v = new int[n+1][m+1][k+1][k+1];
v[1][1][k][k] = 1;
Queue<Node> q = new ArrayDeque<>();
q.add(new Node(1,1,k,k));
while(!q.isEmpty()){
Node cur = q.poll();
if(cur.x == n && cur.y == m){
result = "Yes";
break;
}
int dir = board[cur.x][cur.y];
int nx = cur.x + dx[dir];
int ny = cur.y + dy[dir];
if(!isOut(nx,ny) && v[nx][ny][cur.l][cur.r] == 0){
v[nx][ny][cur.l][cur.r] = v[cur.x][cur.y][cur.l][cur.r] + 1;
q.add(new Node(nx,ny,cur.l,cur.r));
}
int tmpR = cur.r;
int dirR = board[cur.x][cur.y];
for(int i = 1 ; i <= 3 ; i++){
if(tmpR <= 0)
break;
dirR = changeR(dirR);
tmpR--;
nx = cur.x + dx[dirR];
ny = cur.y + dy[dirR];
if(!isOut(nx,ny) && v[nx][ny][cur.l][tmpR] == 0){
v[nx][ny][cur.l][tmpR] = v[cur.x][cur.y][cur.l][cur.r] + 1;
q.add(new Node(nx,ny,cur.l,tmpR));
}
}
int tmpL = cur.l;
int dirL = board[cur.x][cur.y];
for(int i = 1 ; i <= 3 ; i++){
if(tmpL <= 0)
break;
dirL = changeL(dirL);
tmpL--;
nx = cur.x + dx[dirL];
ny = cur.y + dy[dirL];
if(!isOut(nx,ny) && v[nx][ny][tmpL][cur.r] == 0){
v[nx][ny][tmpL][cur.r] = v[cur.x][cur.y][cur.l][cur.r] + 1;
q.add(new Node(nx,ny,tmpL,cur.r));
}
}
}
System.out.println(result);
}
static boolean isOut(int x,int y){
if(x < 1 || x > n || y < 1 || y > m)
return true;
return false;
}
static void print(){
for(int i =1 ; i <= n ; i++){
for(int j =1 ; j <= m ; j++){
System.out.print(board[i][j]+" ");
}
System.out.println();
}
System.out.println();
}
static int changeR(int cur){
return cur + 1 > 3 ? 0 : cur + 1;
}
static int changeL(int cur){
return cur -1 < 0 ? 3 : cur - 1;
}
static class Node{
int x;
int y;
int l;
int r;
Node(int x,int y,int l,int r){
this.x = x;
this.y = y;
this.l = l;
this.r = r;
}
}
}'알고리즘 > 백준' 카테고리의 다른 글
| 백준 28019 (산지니의 여행계획) - java (0) | 2024.05.09 |
|---|---|
| 백준 20366 (같이 눈사람 만들래?) - java (1) | 2024.05.07 |
| 백준 18116 (로봇 조립) - java (1) | 2024.04.28 |
| 백준 13907 (세금) - java (0) | 2024.04.25 |
| 백준 10776 (제국) - java (0) | 2024.04.24 |
- Total
- Today
- Yesterday
- 백준 #3980 #선발 명단
- 백준 #17940 #주식 #자바 #java
- 백준 #18405 #경쟁적 전염
- 자바
- 백준 #16973 #직사각형 탈출
- 17218
- 백준 #4963 #섬의 개수
- 백준 #14863 #서울에서 경산까지 #java #자바
- 백준 #치즈 #2638
- 백준 #5721 #사탕 줍기 대회 #java #자바
- 백준 #28140 #빨강~ 빨강~ 파랑! 파랑! 달콤한 솜사탕! #java #자바
- 백준 #25603 #짱해커 이동식 #java #자바
- 백준 #12014 #주식 #자바 #java
- 올해보다
- 17394
- 백준 #1759 #암호 만들기
- 백준 #1584 #게임 #java #자바
- 백준 #
- 백준 #1325 #효율적인 해킹
- 백준 #2580 #스도쿠
- 백준
- Java
- 백준 #인구 이동 #16234
- 백준 #15686 #치킨 배달
- 백준 #1987 #알파벳 #자바 #java
- 행복합시다.
- 백준 #13549 #숨바꼭질3
- 백준 #2636 #치즈
- 백준 #다리 만들기 #2146
- 자바 #JAVA
| 일 | 월 | 화 | 수 | 목 | 금 | 토 |
|---|---|---|---|---|---|---|
| 1 | 2 | 3 | 4 | 5 | 6 | 7 |
| 8 | 9 | 10 | 11 | 12 | 13 | 14 |
| 15 | 16 | 17 | 18 | 19 | 20 | 21 |
| 22 | 23 | 24 | 25 | 26 | 27 | 28 |