티스토리 뷰

 

처음 스터디하다가 배웠을 때 신기했던 문제다

이 문제는 다익스트라르 풀 수 있다!

 

다익스트라로 어떻게 풀어야할까

 

쓰레기는 최대한 안지나고 쓰레기 옆길도 안지나고싶다

그럼 가중치를 쓰레기에는 5000, 옆길은 1을 줘보자!

 

5000을 주는 이유는 나올 수 없는 값을 주기 위해서다

왜냐면 나중에 5000으로 나눌거라서 ㅎㅎ

 

문제를 푸는 방법을 생각해보자!

 

1. 먼저 가중치를 쓰레기는 5000, 쓰레기 4방향으로는 1을 주자

2. 그리고 다익스트라를 통해 목적지까지 간다면 최소비용으로 가는 길을 찾을 것이다

3. 그럼 우선순위는 빈칸-> 쓰레기 옆길 -> 쓰레기가 된다

4. 마지막으로 쓰레기를 지나쳤다면 5000a , 옆길을 지나치면 b라는 가중치가 있을것이다

  => 5000a+b가 될테니 /5000을 한다면 쓰레기, %5000을한다면 옆을 지난 수를 구하기 가능!

 

비슷한 문제로는 아래!

https://www.acmicpc.net/problem/1261

 

1261번: 알고스팟

첫째 줄에 미로의 크기를 나타내는 가로 크기 M, 세로 크기 N (1 ≤ N, M ≤ 100)이 주어진다. 다음 N개의 줄에는 미로의 상태를 나타내는 숫자 0과 1이 주어진다. 0은 빈 방을 의미하고, 1은 벽을 의미한다. (1, 1)과 (N, M)은 항상 뚫려있다.

www.acmicpc.net

https://www.acmicpc.net/problem/17267

 

17267번: 상남자

CTP의 대표 상남자 영조는 자유롭게 이동하는 것을 좋아한다. 그렇지만 영조는 상남자이기 때문에 위아래로만 간다. 따라서 위, 아래로는 얼마든지 이동할 수 있지만 왼쪽, 오른쪽으로는 이동하지 않는다. 하지만 영조의 행동이 답답한 영조의 친구 보성이는 영조가 위, 아래로만 가는 걸 막기 위해 영조와 같이 다니며 왼쪽으로 최대 L번 오른쪽으로 최대 R번만큼 이동할 수 있게 영조를 도와준다. 영조와 보성이는 지도 밖으로는 나가지 않는다. 갈수 있는 땅, 벽의

www.acmicpc.net

상남자 풀이 

https://sejinik.tistory.com/130

 

[백준] 17267 상남자

다익스트라를 이용하는 문제다 왼쪽 오른쪽으로 최대 L,R만큼 갈 수 있다 그럼 왼쪽으로 갈 때 가중치 100, 오른쪽으로 갈 때 10억을 주자 그리고 다익스트라를 돌려 모든정점에 최단거리를 구하자 그 후 각 정점..

sejinik.tistory.com

 

소스코드

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
#include <iostream>
#include <algorithm>
#include <queue>    
#include <cstring>
using namespace std;
int n, m,Sx,Sy,Fx,Fy;
int map[55][55];
int d[55][55];
int dx[4= { 0,0,-1,1 };
int dy[4= { -1,1,0,0 };
 
bool inner(int x, int y) {
    return (0 <= x && x < n && 0 <= y && y < m);
}
 
void changeCost(int x, int y) {
    map[x][y] = 5000;
    for (int i = 0; i < 4; i++) {
        int nx = x + dx[i];
        int ny = y + dy[i];
        if (inner(nx, ny) && !map[nx][ny]) map[nx][ny] = 1;
    }
}
 
int main() {
    memset(d, -1sizeof(d));
    scanf(" %d %d"&n, &m);
    for (int i = 0; i < n; i++) {
        for (int j = 0; j < m; j++) {
            char c; scanf(" %1c"&c);
            if (c == 'S') Sx = i, Sy = j,map[i][j]=-1;
            if (c == 'F') Fx = i, Fy = j,map[i][j]=-1;
            if (c == 'g') changeCost(i, j);
        }
    }
    map[Sx][Sy] = map[Fx][Fy] = 0;
    priority_queue<pair<intpair<intint>>> pq;
    pq.push(0,{Sx,Sy} });
 
    while (!pq.empty()) {
        int cost = -pq.top().first;
        int x = pq.top().second.first;
        int y = pq.top().second.second;
        pq.pop();
 
        if (d[x][y] != -1continue;
        d[x][y] = cost;
 
        for (int i = 0; i < 4; i++) {
            int nx = x + dx[i];
            int ny = y + dy[i];
            if (!inner(nx, ny)) continue;
            if (d[nx][ny] != -1continue;
            int ncost = -cost - map[nx][ny];
            pq.push({ ncost,{nx,ny} });
        }
    }
    printf("%d %d\n", d[Fx][Fy] / 5000, d[Fx][Fy] % 5000);
}
 
 

'알고리즘 > BOJ' 카테고리의 다른 글

[백준] 12945 재미있는 박스 정리  (0) 2020.02.05
[백준] 10800 컬러볼  (0) 2020.02.05
[백준] 17472 다리 만들기 2  (0) 2020.02.05
[백준] 2502 떡 먹는 호랑이  (1) 2020.02.04
[백준] 2590 색종이  (0) 2020.02.04
댓글
공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
링크
TAG
more
«   2024/04   »
1 2 3 4 5 6
7 8 9 10 11 12 13
14 15 16 17 18 19 20
21 22 23 24 25 26 27
28 29 30
글 보관함