본문 바로가기

ALGORITHM_PRACTICE

백준 13913번: 숨바꼭질 4

백준 13913: 숨바꼭질 4

 

13913번: 숨바꼭질 4

수빈이는 동생과 숨바꼭질을 하고 있다. 수빈이는 현재 점 N(0 ≤ N ≤ 100,000)에 있고, 동생은 점 K(0 ≤ K ≤ 100,000)에 있다. 수빈이는 걷거나 순간이동을 할 수 있다. 만약, 수빈이의 위치가 X일 때 걷는다면 1초 후에 X-1 또는 X+1로 이동하게 된다. 순간이동을 하는 경우에는 1초 후에 2*X의 위치로 이동하게 된다. 수빈이와 동생의 위치가 주어졌을 때, 수빈이가 동생을 찾을 수 있는 가장 빠른 시간이 몇 초 후인지 구하는

www.acmicpc.net

 

예전에 풀었던 숨바꼭질 시리즈인데 오랜만에 풀어서 그런지 시간초과로 한번에 풀지를 못했다. 결국 예전 코드를 참조해서 다시 기억을 되살려서 풀어냈다. DFS를 사용하면 시간초과가 나고 BFS를 사용하는편이 정신건강에 이롭다. 코드 풀이는 간단하다. 앞으로 한칸, 뒤로 한칸, 앞으로 두배 이동 이렇게 세개의 경우만 큐에 푸쉬를하고 가장 먼저 탐색되는 경우가 최소 걸리는 시간이다. 이때 해당 경로로올때 바로 이전 원소를 저장하는 배열을 가지는 배열 변수가 필요하고, 최소 거리를 찾았을 때 이전 노드로 되돌아가면서 벡터에 push하는 방법으로 최소 이동 경로를 파악할 수 있었다.

 

#include<iostream>
#include<queue>

#include<vector>
#define MAX_POS 100001
using namespace std;

int previous[MAX_POS];
bool visited[MAX_POS] = {false};
int n, k;
int result;
queue<pair<int, int>> q;            //first:pos second:dist
vector<int> path;

void bfs(){
    int pos, dist;
    while(!q.empty()){
        pos = q.front().first;
        dist = q.front().second;
        q.pop();
        if(pos == k){
            int t = pos;
            while(t != n){
                path.push_back(t);
                t = previous[t];
            }
            path.push_back(t);
            result = dist;
            return;
        }
        
        if (2 * pos < MAX_POS)
        {
            if (!visited[2 * pos])
            {
                visited[2 * pos] = true;
                previous[2 * pos] = pos;
                q.push({2 * pos, dist + 1});
            }
        }
        if(pos - 1 >= 0){
            if(!visited[pos-1]){
                visited[pos-1] = true;
                previous[pos-1] = pos;
                q.push({pos - 1, dist + 1});
            }
        }
        if(pos+1 < MAX_POS){
            if(!visited[pos+1]){
                visited[pos+1] = true;
                previous[pos+1] = pos;
                q.push({pos + 1, dist + 1});
            }
        }
    }
}

int main(){
    ios_base::sync_with_stdio(false);
    cin.tie(0);
    cout.tie(0);
    cin >> n >> k;
    q.push({n, 0}); 
    bfs();
    cout << result << "\n";
    for(int i = path.size()-1; i >= 0; i--){
        cout << path[i] << " ";
    }
    return 0;
}

'ALGORITHM_PRACTICE' 카테고리의 다른 글

백준 13335번: 트럭  (0) 2019.06.24
백준 11051번: 이항 계수 2  (0) 2019.06.23
백준 11967번: 불켜기  (0) 2019.06.22
백준 1600: 말이 되고픈 원숭이  (0) 2019.06.22
백준 3197번: 백조의 호수  (0) 2019.06.21