본문 바로가기
백준

[백준] code.plus(시뮬레이션과 구현,JAVA)14499번, 주사위 돌리기

by 열정적인 이찬형 2022. 5. 9.

문제 링크

 

14499번: 주사위 굴리기

첫째 줄에 지도의 세로 크기 N, 가로 크기 M (1 ≤ N, M ≤ 20), 주사위를 놓은 곳의 좌표 x, y(0 ≤ x ≤ N-1, 0 ≤ y ≤ M-1), 그리고 명령의 개수 K (1 ≤ K ≤ 1,000)가 주어진다. 둘째 줄부터 N개의 줄에 지

www.acmicpc.net


주의사항

  • JAVA를 사용하여 프로그램을 사용하였습니다.
  • 백준에서 코드를 작성하였을 때 아래 형태에서 Main에서 결과가 출력되어야 합니다.
public class Main{ 	
	public static void main(String[] args){
    }
}

문제 설명


접근 방법

이 문제에 핵심은

1. 지도에서 주사위를 동서남북 방향으로 굴립니다.

2. 지도가 0이면 주사위 바닥면 값을 지도에 저장하고 0이 아니면 바닥면에 지도 값을 저장한 뒤 0을 저장한다.

3. 각 주사위가 움직일 때마다 주사위 윗면을 결과로 출력합니다.

 

사용되는 배열

arr[][] : 입력되는 지도 저장하는 배열

dice[][] : 현재 주사위의 형태를 표현하는 배열

 

주사위가 움직일 때마다 주사위의 값이 저장된 배열이 어떻게 변경되는지 표로 보여드리겠습니다.

먼저 주사위의 기본 값을 아래와 같다고 생각하겠습니다.

0 1 0
2 3 4
0 5 0
0 6 0

주사위를 동쪽으로 이동할 때

0 1 0
6 2 3
0 5 0
0 4 0

[3][1] -> [1][0]

[1][0] -> [1][1]

[1][1] -> [1][2]

[1][2] -> [3][1]

주사위를 서쪽으로 이동할 때

0 1 0
3 4 6
0 5 0
0 2 0

[3][1] -> [1][2]

[1][2] -> [1][1]

[1][1] -> [1][0]

[1][0] -> [3][1]

주사위를 북쪽으로 이동할 때

0 3 0
2 5 4
0 6 0
0 1 0

[0][1] -> [3][1]

[1][1] -> [0][1]

[2][1] -> [1][1]

[3][1] -> [2][1]

주사위를 남쪽으로 이동할 때

0 6 0
2 1 4
0 3 0
0 5 0

[3][1] -> [0][1]

[2][1] -> [3][1]

[1][1] -> [2][0]

[0][1] -> [1][1]

 

주사위 움직일 때 바닥면이 되는 값은

0 6(북) 0
2(서) 1 4(동)
0 3(남) 0
0 5 0

 

주사위 움직일 때 주사위 배열 변경되는 방법과 지도의 값들의 변화를 이용하여 알고리즘을 작성하면 됩니다.

 

문제를 해결한 알고리즘의 과정입니다.

1. 입력값들을 받습니다.

2. 시작 위치에서 명령값에 따라 주사위를 움직이고 주사위의 배열의 값과 지도 값을 변경합니다.

3. 변경된 후 주사위의 윗면인 dice[1][1]을 BufferedWriter 저장합닏다.

4. 모든 명령이 끝난뒤 BufferedWriter에 저장된 모든 윗면의 값들을 출력합니다.

 

  • BufferedReader를 사용하여 입력 값을 받았습니다.
  • StringTokenizer를 이용하여 N×M 지도와 N,M,x,yK개의 명령어를 나누었습니다.
  • 명령어에 따른 주사위 배열을 변경하는 diceChange함수를 만들었습니다.
  • K diceChange함수를 실행하고 각 주사위 윗면을 BufferedWriter 저장하였습니다.
  • BufferedWriter에 저장된 값을 결과로 출력하였습니다
  • diceChange함수는 dice배열와 위에서 설명한 규칙을 통하여 변경하는 함수입니다.

결과 코드

import java.util.*;
import java.io.*;
public class Main{
	static int N,M,x,y,K;
	static int[][] arr, dice;	//지도,주사위 배열
	static int[] dx = {0,0,-1,1};	//동서북남 x값 변경
	static int[] dy = {1,-1,0,0};	//동서북남 y값 변경
    public static void main(String[] args) throws IOException{
    	BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        //입력값 처리하는 BufferedReader
    	BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(System.out));
        //결과값 출력하는 BufferedWriter
    	StringTokenizer st = new StringTokenizer(br.readLine()," ");
    	dice = new int[4][3];
    	N = Integer.parseInt(st.nextToken());
    	M = Integer.parseInt(st.nextToken());
    	x = Integer.parseInt(st.nextToken());
    	y = Integer.parseInt(st.nextToken());
    	K = Integer.parseInt(st.nextToken());
    	arr = new int[N][M];
    	//지도 배열 초기화
    	for(int i=0;i<N;i++) {
    		st = new StringTokenizer(br.readLine()," ");
    		for(int j=0;j<M;j++) {
    			arr[i][j] = Integer.parseInt(st.nextToken());
    		}
    	}
    	st = new StringTokenizer(br.readLine()," ");
    	int size = st.countTokens();
        //K번 명령 실행
    	for(int i=0;i<size;i++) {
    		int command = Integer.parseInt(st.nextToken());
    		int tempX = x + dx[command-1];	//x값 변경
    		int tempY = y + dy[command-1];	//y값 변경
            //이동시 지도 범위에 안
    		if(tempX>=0 && tempY>=0 && tempX<N && tempY<M) {
    			x = tempX;
    			y = tempY;
    		}else		//이동시 지도 범위 밖
    			continue;
    		int diceX = 1 + dx[command-1];
    		int diceY = 1 + dy[command-1];
    		if(arr[x][y] == 0)	//지도 값 0일 때
    			arr[x][y] = dice[diceX][diceY];
    		else {		//지도 값 0 아닐 때
    			dice[diceX][diceY] = arr[x][y];
    			arr[x][y] = 0;
    		}
    		diceChange(command);		//함수 실행
    		bw.write(dice[1][1] + "\n");	//주사위 윗면 BufferedWriter 저장
    	}
    	bw.flush();		//결과 출력
    	bw.close();
    	br.close();

    }
    //규칙을 이용하여 주사위 배열 변경하는 함수
    static void diceChange(int command) {
    	if(command==1) {		//동
    		int temp = dice[3][1];
    		dice[3][1] = dice[1][2];
    		dice[1][2] = dice[1][1];
    		dice[1][1] = dice[1][0];
    		dice[1][0] = temp;
    	}else if(command==2) {		//서
    		int temp = dice[3][1];
    		dice[3][1] = dice[1][0];
    		dice[1][0] = dice[1][1];
    		dice[1][1] = dice[1][2];
    		dice[1][2] = temp;
    	}else if(command==3) {		//북
    		int temp = dice[0][1];
    		for(int i=0;i<3;i++) {
    			dice[i][1] = dice[i+1][1]; 
    		}
    		dice[3][1] = temp;

    	}else {		//남
    		int temp = dice[3][1];
    		for(int i=3;i>0;i--) 
    			dice[i][1] = dice[i-1][1]; 
    		dice[0][1] = temp;
    	}
    	return;
    }
}

댓글