알고리즘 문제/백준
[백준 - Java] 14499번 : 주사위 굴리기 (삼성 SW 역량 테스트 기출 문제)
건복치
2021. 2. 10. 01:55
반응형
문제
설명
주사위 굴리는걸 어떻게 해야 하나 고민하는데 시간을 많이 쏟았다 ㅠ____ㅠ
근데 주사위만 굴리면 다 해결되는 문제. ㄹㅇ 아래 주사위를 기준으로 상하좌우 굴려보면 규칙을 찾을 수 있다.
2
4 1 3
5
6
나는 주사위의 Top, Bottom, Up, Down, Left, Right 6면을 모두 고려해 주사위를 굴렸는데 이렇게 하지 않아도 된다.
Top, Up, Left의 3개의 면에서 -7을 해주면 무조건 반대면이 나오기 때문에 이 3면만 가지고 해결할 수 있다.
Top을 기준으로 상 하 좌우 4방향으로 굴려보자
- ➡︎ 오른쪽으로 굴리는 경우 (Up, Down은 그대로)
- Top -> Right
- Right -> Bottom
- Bottom -> Left
- Left -> Top
- ⬅︎ 왼쪽으로 굴리는 경우 (Up, Down은 그대로)
- Top -> Left
- Left -> Bottom
- Bottom -> Right
- Right -> Top
- ⬇︎ 아래쪽으로 굴리는 경우 (Left, Right는 그대로)
- Top -> Down
- Down -> Bottom
- Bottom -> Up
- Up -> Top
- ⬆︎ 위쪽으로 굴리는 경우 (Left, Right는 그대로)
- Top -> Up
- Up -> Bottom
- Bottom -> Down
- Down -> Top
전체 코드
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.util.StringTokenizer;
public class Main {
static int N, M;
static int[][] map;
static int[] dx = {-1, 0, 1, 0}; // 상 좌 하 우 순서
static int[] dy = {0, -1, 0, 1};
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());
int x = Integer.parseInt(st.nextToken());
int y = Integer.parseInt(st.nextToken());
int K = Integer.parseInt(st.nextToken());
map = new int[N][M];
for(int i = 0; i < N; i++) {
st = new StringTokenizer(br.readLine());
for(int j = 0; j < M; j++) {
map[i][j] = Integer.parseInt(st.nextToken());
}
}
// 초기 주사위 면의 상태 - top, up, down, left, right, bottom 순서
Dice curDice = new Dice(0, 1, 2, 3, 4, 5);
int[] dice = new int[6]; // 주사위 각 면의 값을 저장할 배열
st = new StringTokenizer(br.readLine());
for(int i = 0; i < K; i++) {
int k = Integer.parseInt(st.nextToken());
// 굴리기 전 현재 주사위 면의 상태
int t = curDice.top;
int u = curDice.up;
int d = curDice.down;
int l = curDice.left;
int r = curDice.right;
int b = curDice.bottom;
Dice nextDice;
// 방향을 상좌하우 0 1 2 3 순서로 만들고, nextDice에 굴린 후의 주사위 면의 상태 저장
if(k == 1) { // 오른쪽 방향으로 굴릴 경우
k = 3;
nextDice = new Dice(l, u, d, b, t, r);
} else if(k == 2) { // 왼쪽 방향으로 굴릴 경우
k = 1;
nextDice = new Dice(r, u, d, t, b, l);
} else if(k == 3) { // 위쪽 방향으로 굴릴 경우
k = 0;
nextDice = new Dice(u, b, t, l, r, d);
} else { // 아래쪽 방향으로 굴릴 경우
k = 2;
nextDice = new Dice(d, t, b, l, r, u);
}
// 굴러갈 위치
int nx = x + dx[k];
int ny = y + dy[k];
// 범위를 벗어나는 경우 -> 해당 명령 무시
if(nx < 0 || nx >= N || ny < 0 || ny >= M) {
continue;
}
// 굴릴 수 있는 경우, 현재 주사위를 굴린 후의 주사위 상태로 변경
curDice = nextDice;
x = nx; // 주사위 위치도 변경
y = ny;
// 이동한 칸에 쓰여 있는 수가 0이면, 주사위의 바닥면에 쓰여 있는 수가 칸에 복사
if(map[nx][ny] == 0) {
map[nx][ny] = dice[nextDice.bottom];
System.out.println(dice[nextDice.top]);
} else { // 0이 아닌 경우에는 칸에 쓰여 있는 수가 주사위의 바닥면으로 복사되며,
dice[nextDice.bottom] = map[nx][ny];
map[nx][ny] = 0; // 칸에 쓰여 있는 수는 0
System.out.println(dice[nextDice.top]);
}
}
}
}
class Dice {
int top, up, down, left, right, bottom;
Dice(int top, int up, int down, int left, int right, int bottom) {
this.top = top;
this.up = up;
this.down = down;
this.left = left;
this.right = right;
this.bottom = bottom;
}
}
GITHUB
github.com/KwonMinha/BOJ/blob/master/BOJ%2314499/src/Main.java
반응형