백준 숨바꼭질 [c++]
숨바꼭질 실버1
문제
수빈이는 동생과 숨바꼭질을 하고 있다. 수빈이는 현재 점 N(0 ≤ N ≤ 100,000)에 있고, 동생은 점 K(0 ≤ K ≤ 100,000)에 있다. 수빈이는 걷거나 순간이동을 할 수 있다. 만약, 수빈이의 위치가 X일 때 걷는다면 1초 후에 X-1 또는 X+1로 이동하게 된다. 순간이동을 하는 경우에는 1초 후에 2*X의 위치로 이동하게 된다.
수빈이와 동생의 위치가 주어졌을 때, 수빈이가 동생을 찾을 수 있는 가장 빠른 시간이 몇 초 후인지 구하는 프로그램을 작성하시오.
문제 풀이
- 일차원배열이지만 그래프탐색 문제이다.
- bfs를 이용하는것이 적절해보임.
- 탑색까지 걸린 level을 count하기 위해 위치정보와 cnt를 pair로 큐에 삽입한다.
- 실수 1. visited를 만들어놓고 방문할때마다 표시해주지 않는 실수함.
- 실수 2. 수빈이와 동생의 위치가 동일한 경우 0이 아닌 1로 표기된다. (0으로 표기되어야 함.) 내가 작성한 코드의 경우 다음위치가 동생위치인지 비교하기 때문에 예외처리가 필요했다.
코드
#include <iostream>
#include <algorithm>
#include <queue>
using namespace std;
int n, k;
int area[100001];
int visited[100001];
queue<pair<int, int> > q;
int cnt = 0;
void init()
{
for(int i = 0; i <= 100000; i++)
{
area[i] = 0;
visited[i] = 0;
}
}
void bfs(int s){
visited[s] = 1;
q.push(make_pair(s, cnt));
while(!q.empty()){
int ns = q.front().first;
cnt = q.front().second;
q.pop();
visited[ns] = 1;
int ns_f = ns + 1;
int ns_b = ns - 1;
int ns_t = 2 * ns;
if(ns_f == k || ns_b == k || ns_t == k){
cout << cnt + 1 << endl;
return;
}
if(ns_f >= 0 && ns_f <= 100000 && visited[ns_f] == 0){
q.push(make_pair(ns_f, cnt + 1));
}
if(ns_b >= 0 && ns_b <= 100000 && visited[ns_b] == 0){
q.push(make_pair(ns_b, cnt + 1));
}
if(ns_t >= 0 && ns_t <= 100000 && visited[ns_t] == 0){
q.push(make_pair(ns_t, cnt + 1));
}
}
}
int main()
{
cin >> n >> k;
init();
if(n != k){
bfs(n);
} else{
cout << 0 << endl;
}
return 0;
}
총평
- bfs에서 정답이 트리의 어떤 레벨인지 확인하기 위해 위치와 level을 pair로 다루는 방법을 알 수 있었음.
- 예외처리 항상 주의!