12100 2048 (Easy)

RushBsite·2022년 8월 1일
0

BaekJoon

목록 보기
8/11
post-thumbnail

2048 (Easy)


문제

2048 게임은 4×4 크기의 보드에서 혼자 즐기는 재미있는 게임이다. 이 링크를 누르면 게임을 해볼 수 있다.

이 게임에서 한 번의 이동은 보드 위에 있는 전체 블록을 상하좌우 네 방향 중 하나로 이동시키는 것이다. 이때, 같은 값을 갖는 두 블록이 충돌하면 두 블록은 하나로 합쳐지게 된다. 한 번의 이동에서 이미 합쳐진 블록은 또 다른 블록과 다시 합쳐질 수 없다. (실제 게임에서는 이동을 한 번 할 때마다 블록이 추가되지만, 이 문제에서 블록이 추가되는 경우는 없다)

입력

첫째 줄에 보드의 크기 N (1 ≤ N ≤ 20)이 주어진다. 둘째 줄부터 N개의 줄에는 게임판의 초기 상태가 주어진다. 0은 빈 칸을 나타내며, 이외의 값은 모두 블록을 나타낸다. 블록에 쓰여 있는 수는 2보다 크거나 같고, 1024보다 작거나 같은 2의 제곱꼴이다. 블록은 적어도 하나 주어진다.

출력

최대 5번 이동시켜서 얻을 수 있는 가장 큰 블록을 출력한다

예시

풀이

move 함수에서 각 방향별로 다르게 grid의 요소를 추출하고, stack에 쌓아서 해결하는 방향으로 구현했다.
DFS의 depth 조건을 유심히 보지 않아 시간이 걸린 문제.

#include <bits/stdc++.h>

using namespace std;

int N, M;
int answer = -1;
vector<vector<int>> grid(20,vector<int>(20));

void combine(stack<pair<int, bool>>&_s, int x) {
	if (_s.empty())
		_s.push({ x,0 });
	else {
		if (_s.top().second == 0 && _s.top().first == x) {
			_s.pop(); _s.push({ 2 * x,1 });
		}
		else
			_s.push({ x,0 });
	}
	return;
}

vector<vector<int>> move(int d, vector<vector<int>> v) {
	switch (d)
	{
	case(0): //up
		for (int j = 0; j < N; j++) {
			stack<pair<int, bool>> s;
			for (int i = 0; i < N; i++) {
				int val = v[i][j];
				if (val == 0) continue;
				else
					combine(s, val);
			}
			//update grid
			int idx = s.size();
			for (int i = idx - 1; i >= 0; i--) {
				v[i][j] = s.top().first;
				s.pop();
			}
			for (int i = idx; i < N; i++)
				v[i][j] = 0;
		}
		
		break;
	case(1): // down
		for (int j = 0; j < N; j++) {
			stack<pair<int, bool>> s;
			for (int i = N-1; i >= 0; i--) {
				int val = v[i][j];
				if (val == 0) continue;
				else
					combine(s, val);
			}
			//update grid
			int idx = s.size();
			for (int i = N - idx; i < N; i++) {
				v[i][j] = s.top().first;
				s.pop();
			}
			for (int i = 0; i < N-idx; i++)
				v[i][j] = 0;
		}
		break;
	case(2): // left
		for (int i = 0; i < N; i++) {
			stack<pair<int, bool>> s;
			for (int j = 0; j < N; j++) {
				int val = v[i][j];
				if (val == 0) continue;
				else
					combine(s, val);
			}
			//update grid
			int idx = s.size();
			for (int j = idx - 1; j >= 0; j--) {
				v[i][j] = s.top().first;
				s.pop();
			}
			for (int j = idx; j < N; j++)
				v[i][j] = 0;
		}
		break;
	case(3): // right
		for (int i = 0; i < N; i++) {
			stack<pair<int, bool>> s;
			for (int j = N - 1; j >= 0; j--) {
				int val = v[i][j];
				if (val == 0) continue;
				else
					combine(s, val);
			}
			//update grid
			int idx = s.size();
			for (int j = N - idx; j < N; j++) {
				v[i][j] = s.top().first;
				s.pop();
			}
			for (int j = 0; j < N - idx; j++)
				v[i][j] = 0;
		}
		break;
	}

	return v;
}

void findMax(vector<vector<int>> _grid) {
	for (auto& i : _grid) {
		answer = max(answer, *max_element(i.begin(), i.end()));
	}
}

void dfs(int depth, vector<vector<int>> _grid) {
	if (depth >= 5) {
		findMax(_grid);
		return;
	}
	for (int i = 0; i < 4; i++) {
		switch (i)
		{
		case (0): dfs(depth+1,move(i,_grid));
			break;
 		case (1): dfs(depth+1,move(i,_grid));
			break;
		case (2): dfs(depth+1,move(i,_grid));
			break;
		case (3): dfs(depth+1,move(i,_grid));
			break;
		default:
			break;
		}
	}
}

int main() {
	cin >> N;
	//input
	for (int i = 0; i < N; i++) {
		for (int j = 0; j < N; j++) {
			int t;
			cin >> t; grid[i][j] = t;
		}
	}

	dfs(0,grid);
	cout << answer << "\n";
	return 0;
}
profile
게임 기획/개발 지망생

0개의 댓글