<링크>
https://school.programmers.co.kr/learn/courses/30/lessons/43162
프로그래머스
코드 중심의 개발자 채용. 스택 기반의 포지션 매칭. 프로그래머스의 개발자 맞춤형 프로필을 등록하고, 나와 기술 궁합이 잘 맞는 기업들을 매칭 받으세요.
programmers.co.kr
<문제>
- n개의 섬 사이에 다리를 건설하는 비용(costs)이 주어질 때, 최소의 비용으로 모든 섬이 서로 통행 가능하도록 만들 때 필요한 최소 비용을 return 하도록 solution을 완성하세요.
- 다리를 여러 번 건너더라도, 도달할 수만 있으면 통행 가능하다고 봅니다. 예를 들어 A 섬과 B 섬 사이에 다리가 있고, B 섬과 C 섬 사이에 다리가 있으면 A 섬과 C 섬은 서로 통행 가능합니다.
<제한사항>
- 섬의 개수 n은 1 이상 100 이하입니다.
- costs의 길이는 ((n-1) * n) / 2이하입니다.
- 임의의 i에 대해, costs[i][0] 와 costs[i] [1]에는 다리가 연결되는 두 섬의 번호가 들어있고, costs[i] [2]에는 이 두 섬을 연결하는 다리를 건설할 때 드는 비용입니다.
- 같은 연결은 두 번 주어지지 않습니다. 또한 순서가 바뀌더라도 같은 연결로 봅니다. 즉 0과 1 사이를 연결하는 비용이 주어졌을 때, 1과 0의 비용이 주어지지 않습니다.
- 모든 섬 사이의 다리 건설 비용이 주어지지 않습니다. 이 경우, 두 섬 사이의 건설이 불가능한 것으로 봅니다.
- 연결할 수 없는 섬은 주어지지 않습니다.
<입력 및 출력>
<아이디어>
1. 문제에서 최소 비용이라고 했으니.. MST를 생각해보자
2. MST를 쓰려면 Edge라는 class를 만들어서, from, to, weight를 각각 생성해야겠지?
3. 생성한다음.. 이제 Edge라는 걸 List에 담아서, 계속 하나씩 Edge라는 객체를 만들어서 담아주시고...
4. 정렬해서 크루스칼 돌립시당. (간적크, 간만프) ㅎ 난 크루스칼할래...
5. 대신..!!! 정렬해서 가져와야해요? 안그럼 엉망으로 들어가있어서 슬퍼짐.. (나도 알고싶지 않았어..)
6. unionfind, findSet해서 최소비용구하기!
<풀이 - Java >
import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;
class Solution {
public static class Edge {
int from, to;
int weight;
public Edge(int from, int to, int weight) {
super();
this.from = from;
this.to = to;
this.weight = weight;
}
@Override
public String toString() {
return "Edge [from=" + from + ", to=" + to + ", weight=" + weight + "]";
}
}
public static Edge[] edges;
public static Map<Integer, Integer> roots;
public int solution(int n, int[][] costs) {
int k = costs.length;
edges = new Edge[k];
roots = new HashMap<>();
for (int i = 0; i < n; i++)
roots.put(i, i);
for (int i = 0; i < k; i++)
edges[i] = new Edge(costs[i][0], costs[i][1], costs[i][2]);
Arrays.sort(edges, (o1, o2) -> o1.weight - o2.weight);
// 크루스칼
int cnt = 0;
int totalCost = 0;
for (int i = 0; i < costs.length; i++) {
if (unionFind(edges[i].from, edges[i].to)) {
totalCost += edges[i].weight;
cnt++;
}
if (cnt == n - 1){
break;
}
}
return totalCost;
}
// 루트 경로찾기
public static int findSet(int v) {
if (v == roots.get(v)){
return v;
}
roots.put(v, findSet(roots.get(v)));
return roots.get(v);
}
// 유니온 파인드
public static boolean unionFind(int a, int b) {
int A = findSet(a);
int B = findSet(b);
if (A == B){
return false;
}
roots.put(B, A);
return true;
}
}
'알고리즘 > 프로그래머스' 카테고리의 다른 글
<프로그래머스> 문자열 내 마음대로 정렬하기 (0) | 2024.09.23 |
---|---|
<프로그래머스> 미로 탈출 (2) | 2024.09.11 |
<프로그래머스> 네트워크 (0) | 2024.09.05 |
<프로그래머스> 게임 맵 최단거리 (2) | 2024.09.04 |
<프로그래머스> 영어 끝말잇기 (1) | 2024.09.04 |