[삼성코테기출문제] 주사위 굴리기

2 분 소요

주사위 굴리기

문제

이 문제도 전형적인 시뮬레이션 문제이다. 뱀을 풀었던 경험으로 접근하여 풀었는데, 주사위를 어떻게 처리해줄 것인가?가 관건이었다.

문제

문제 풀이

입출력 조건
입력

처음 주어지는 주사위의 정보가 힌트다! 라는 생각이 바로 떠올랐다. 각 면에 쓰여지는 숫자를 Dice라는 배열에 저장해두고 주사위가 굴려질때마다 조건에 맞게 바꿔주는 방법을 생각했다.

int Cmd[MAX_K];
int Dice[6];
int dir[4][6] =
{
	{2, 1, 5, 0, 4, 3},
	{3, 1, 0, 5, 4, 2},
	{1, 5, 2, 3, 0, 4},
	{4, 0, 2, 3, 5, 1},
};

… 생략 …

void Command(int c) {
	int tmp_Dice[6];
	int idx = Cmd[c];
	for (int i = 0; i < 6; i++) tmp_Dice[i] = Dice[dir[idx - 1][i]];
	for (int i = 0; i < 6; i++)Dice[i] = tmp_Dice[i];
}

이 부분이 주사위를 처리해주는 부분인데, 주어지는 명령의 개수 K만큼의 명령을 Cmd에 받아두고 명령의 방향(1:동, 2: 서, 3: 북, 4: 남)에 따라 Dice의 인덱스를 바꿔주는 dir을 만들고 그 부분을 처리하는 함수 Command를 만들었다.
입력

이런식으로 Dice의 기본 인덱스를 가운데 전개도와 같이 생각하고 (바닥을 보는면(1), 하늘을 보는면(6)) 각 방향으로 명령이 들어오면 주사위를 굴린 후를 생각하여 Dice의 인덱스가 바뀌어야한다.

풀이 과정

  1. 먼저 지도의 크기, 주사위의 위치, 지도의 정보, 명령의 정보를 입력받고, 주사위의 위치를 큐에 push한다.
  2. 주사위의 현재 위치를 받고, 다음 방향을 의미하는 nx,ny에 명령의 방향으로 굴린 좌표를 저장한다.
  3. 주사위가 구를 수 있는 범위라면 현재 명령의 방향으로 주사위 정보를 바꿔준다.
  4. 굴린 후의 주사위의 위치의 지도의 숫자가 0이면 주사위와 지도가 닿는 면의 주사위 숫자를 지도에 복사한다.
    만약 지도의 숫자가 0이 아니라면 지도의 숫자를 바닥과 닿은 주사위의 면에 지도의 숫자를 복사하고 지도의 숫자를 0으로 바꾼다.
  5. 그리고 하늘을 바라보고있는 주사위의 면의 숫자를 출력하고, 주사위의 위치를 push한다.
  6. 만약 주사위의 다음 위치가 범위를 벗어나면 주사위는 움직일 수 없으므로 아무 작업을 하지않고 주사위의 위치를 push한다.
  7. 위 과정을 명령의 개수만큼 반복한다.

#include<iostream>

using namespace std;
const int MAX = 20;
const int MAX_K = 1000;
int N, M, K;
int Map[MAX][MAX];

int Cmd[MAX_K];
int Dice[6];

int dx[4] = { 1,-1,0,0 }, dy[4] = { 0,0,-1,1 };
int dir[4][6] =
{
	{2, 1, 5, 0, 4, 3},
	{3, 1, 0, 5, 4, 2},
	{1, 5, 2, 3, 0, 4},
	{4, 0, 2, 3, 5, 1},
};
typedef struct Pos {
	int x, y;
};
Pos Q[1000]; int f, r;
void push(int x, int y) { Q[r++] = { x,y }; }
Pos pop() { return Q[f++]; }

void Init() {
	int x, y;
	cin >> N >> M >> y >> x >> K;
	for (int i = 0; i < N; i++) {
		for (int j = 0; j < M; j++) {
			cin >> Map[i][j];
		}
	}
	for (int i = 0; i < K; i++)
		cin >> Cmd[i];
	push(x, y);
}
void Command(int c) {
	int tmp_Dice[6];
	int idx = Cmd[c];
	for (int i = 0; i < 6; i++) tmp_Dice[i] = Dice[dir[idx - 1][i]];
	for (int i = 0; i < 6; i++)Dice[i] = tmp_Dice[i];
}
void Process() {
	for (int i = 0; i < K; i++) {
		Pos cur = pop();
		int nx, ny;
		int c = Cmd[i] - 1;
		nx = cur.x + dx[c];
		ny = cur.y + dy[c];
		if (ny >= 0 && nx >= 0 && ny < N&&nx < M) {
			Command(i);
			if (Map[ny][nx] == 0) {
				Map[ny][nx] = Dice[0];
			}
			else {
				Dice[0] = Map[ny][nx];
				Map[ny][nx] = 0;
			}
			cout << Dice[5] << endl;
			push(nx, ny);
		}
		else push(cur.x, cur.y);
	}
}
void Solution() {
	Init();
	Process();
}
int main() {
	freopen("05.in", "r", stdin);
	cin.tie(NULL);
	ios::sync_with_stdio(false);
	Solution();
	return 0;
}

댓글남기기