[적용한 알고리즘]

MST(크루스칼)

 

[아이디어]

하고 싶은게 두 가지다.

1. 두 마을로 쪼개고 싶다. (최소한의 경로만 남겨놓고)

2. 유지비를 최소로 하고 싶다. 

 

MST 를 만들어야할 것 같은데, 두 마을로 어떻게 쪼갤 지 고민을 하다보면,

우선 MST 를 만든 뒤, 만든 간선 중 가장 값이 큰 간선 하나를 제외시켜버리면 된다.

 

근데 크루스칼 알고리즘에서는 값이 가장 큰 간선이 가장 마지막에 추가되므로,

마지막 반복문을 안돌리면 되는 거다.

 

[교훈]

그래프..

 

<코드>

#include <cstdio>
#include <vector>
#include <algorithm>
#include <queue>
using namespace std;

struct Edge {
    int start, end, cost;
    bool operator < (const Edge &other) const {
        return cost < other.cost;
    }
};

int Parent[100001];

int Find(int x){
    if (x == Parent[x]){
        return x;
    }
    return Parent[x] = Find(Parent[x]);
}

bool Merge(int x, int y){
    x = Find(x);
    y = Find(y);

    if (x == y) return false;
    Parent[x] = y;
    return true;
}

int main(){
    int N, M;
    scanf("%d %d", &N, &M);

    for (int i = 1; i <= N; i++){
        Parent[i] = i;
    }

    vector<Edge> E;
    for (int i = 0; i < M; i++){
        int from, to, cost;
        scanf("%d %d %d", &from, &to, &cost);
        E.push_back({from, to, cost});
    }

    sort(E.begin(), E.end());
    int ans = 0;
    int cnt = 0;

    for (int i = 0; i < M; i++){
        Edge cur = E[i];

        if (Merge(cur.start, cur.end)){
            ans += cur.cost;
            cnt++;
        }

        if (cnt == N - 2){
            break;
        }
    }

    printf("%d\n", ans);
    return 0;
}

'Algorithm > BOJ' 카테고리의 다른 글

[백준] 1994번 등차수열  (2) 2020.02.28
[백준] 2099번 The game of death  (0) 2020.02.03
[백준] 1613번 역사  (0) 2020.02.01
[백준] 1854번 K번째 최단경로 찾기  (0) 2020.02.01
[백준] 1507번 궁금한 민호  (0) 2020.02.01

+ Recent posts