📙 Algorithm Solving/Java
📙[Algo] 24.05.09 알고리즘
혜덕hyeduck
2024. 5. 9. 18:14
알고리즘 문제) BOJ 1368. 물대기
문제 요약
- N개의 논에 물을 대려고 한다.
- 물을 대는 방법에는 두 가지가 존재
- 직접 논에 우물을 파는 것
- 이미 물을 대고 있는 다른 논으로부터 물을 끌어오는 것
- 각각의 논에 대해 우물을 파는 비용과 논들 사이에 물을 끌어오는 비용들이 주어졌을 때, 논에 물을 대는 최소 비용 찾기
시간 제한
- 2초
입력
- 첫째 줄 : 논의 수N
- 1 ≤ N ≤ 300
- 다음 N개의 줄에 i번째 논에 우물을 팔 때 드는 비용 Wi가 순서대로 주어짐
- 1 ≤ Wi ≤ 10만
- 다음 N개의 줄에 각 줄에 N개의 수가 들어오는데, i번째 논과 j번째 논을 연결하는데 드는 비용 Pi,j를 의미
- 1 ≤ Pi ≤ 10만
출력
- 모든 논에 물을 대는데 필요한 최소 비용 출력
접근법
- 그냥 자기 자신을 파는데 드는 비용은 가상 노드 0번을 만들어서 해당 노드로의 간선 비용으로 가정한다.
- 그리고 나서 MST 로 푸는 문제였다.
코드
//
import java.io.*;
import java.util.*;
public class Main {
static int N;
static int[] cost = new int[310];
static int[] parent = new int[310];
static boolean[] isWater = new boolean[310];
static ArrayList<int[]> graph = new ArrayList<>();
static int find(int x) {
if (parent[x] == x) return x;
parent[x] = find(parent[x]);
return parent[x];
}
static void union(int a, int b) {
a = find(a);
b = find(b);
if (a == b) return;
parent[b] = a;
}
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st;
N = Integer.parseInt(br.readLine());
// 우물파는 비용이 가장 적은 우물 찾으며 비용 입력 받기
for (int i = 1; i <= N; i++) {
cost[i] = Integer.parseInt(br.readLine());
}
graph = new ArrayList<>();
int c;
for (int i = 1; i <= N; i++) {
st = new StringTokenizer(br.readLine());
for (int j = 1; j <= N; j++) {
c = Integer.parseInt(st.nextToken());
if (i == j) {
graph.add(new int[]{i, 0, cost[j]});
graph.add(new int[]{0, i, cost[j]});
} else {
graph.add(new int[]{i, j, c});
}
}
}
// 비용 기준 오름차순 정렬
Collections.sort(graph, new Comparator<int[]>() {
@Override
public int compare(int[] o1, int[] o2) {
return o1[2] - o2[2];
}
});
// 부모 배열 초기화(자기 자신)
for (int i = 0; i < 310; i++) {
parent[i] = i;
}
// 크루스칼 알고리즘
int v1, v2;
int answer = 0;
for (int i = 0; i < graph.size(); i++) {
v1 = graph.get(i)[0];
v2 = graph.get(i)[1];
c = graph.get(i)[2];
if (find(v1) == find(v2)) continue;
union(v1, v2);
answer += c;
}
System.out.println(answer);
br.close();
}
}