본문 바로가기
코딩테스트 준비/백준

[백준/BOJ][C++] 12789번 도키도키 간식드리미

by 스테디코디스트 2023. 8. 23.
반응형

<문제 소개>


<소스 코드>

#include <iostream>
#include <stack>
#include <queue>
using namespace std;

int main()
{
	// 쓰레드 환경이 아닐때 버퍼를 분리하여 처리속도를 빠르게 해줌
	ios_base::sync_with_stdio(false);
	cin.tie(NULL);
	cout.tie(NULL);

	int N;
	cin >> N;

	queue<int> curLine; // 현재 줄 
	stack<int> otherLine; // 또 다른 줄

	for (int i = 0; i < N; i++)
	{
		int x;
		cin >> x;

		curLine.push(x);
	}

	int checkNum = 1;

	while (true)
	{
		if (!curLine.empty() && curLine.front() == checkNum)
		{
			// 현재 줄에 순서에 맞는 번호가 있는 경우
			curLine.pop();
			checkNum++;
		}
		else if (!otherLine.empty() && otherLine.top() == checkNum)
		{
			// 또 다른 줄에 순서에 맞는 번호가 있는 경우
			otherLine.pop();
			checkNum++;
		}
		else
		{
			if (curLine.empty()) break;

			// 순서에 맞는 번호가 없는 경우
			otherLine.push(curLine.front()); // 현재 줄의 맨 앞 사람을 또 다른 줄에 넣음
			curLine.pop();
		}
	}

	if (otherLine.empty())
	{
		cout << "Nice";
	}
	else
	{
		cout << "Sad";
	}	

	return 0;
}

<풀이과정>

1. 현재 줄을 의미하는 큐 curLine과 또 다른 줄을 의미하는 스택 otherLine을 선언한다.

2. N만큼 입력받으면서 큐 curLine에 입력을 push하여 저장한다.

3. 간식을 받을 번호를 체크할 checkNum을 1로 선언한다.

4. while 반복문을 돌면서 3가지 경우에 대해 체크한다.

5-1. 현재 줄에 순서에 맞는 번호가 있는 경우

5-2. curLine이 비어있지 않고 curLine의 맨 앞 숫자가 현재 간식을 받을 번호 checkNum이라면 pop을 이용해 해당 학생을 현재 줄에서 빼고 간식을 받을 번호 checkNum을 하나 증가시킨다.

5-3. 또 다른 줄에 순서에 맞는 번호가 있는 경우

5-4. otherLine이 비어있지 않고, checkNum이 otherLine의 맨 앞 숫자와 같다면, 5-2의 과정을 curLine이 아닌 otherLine에 대해 진행한다. 즉 otherLine에서 pop을 진행하고 checkNum을 1 증가시킨다.

5-5. 그 외의 경우 순서에 맞는 번호가 없다면, 먼저 curLine이 비어있는지를 확인하여 비어있다면 반복문을 끝내고 그렇지 않으면 otherLine에 curLine의 맨 앞 사람을 추가해주고 curLine의 맨 앞 사람은 pop을 이용해 빼준다.

6. while 반복문이 끝난 뒤 otherLine이 비어있다면 무사히 모든 사람이 간식을 받은 경우이므로 Nice를 출력하고, 그렇지 않으면 Sad를 출력해준다.


<코멘트>

큐와 스택을 이용해 야무지게 풀었다!


<제출결과>