[Programmers] 지형 이동 (62050번) - Java Solution
문제
- https://programmers.co.kr/learn/courses/30/lessons/62050
기억할 점
- comparable 구현을 통한 구현한 객체의 sort 방법
- MST 구현 - 크루스칼, 프림 알고리즘
- 자주 활용되는 union-find 알고리즘
Solution
import java.io.IOException;
import java.util.ArrayDeque;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.Deque;
import java.util.List;
class Solution {
class Edge implements Comparable<Edge> {
int cost;
int[] edge;
public Edge(int cost, int[] edge) {
this.cost = cost;
this.edge = edge;
}
@Override
public int compareTo(Edge e) {
return this.cost - e.cost;
}
public int getCost() {
return this.cost;
}
public int[] getEdge() {
return this.edge;
}
}
int findParent(int[] parent, int targetGroup) {
if (targetGroup == parent[targetGroup]) {
return targetGroup;
}
return parent[targetGroup] = findParent(parent, parent[targetGroup]);
}
boolean isSameParent(int[] parent, int targetGroup1, int targetGroup2) {
return findParent(parent, targetGroup1) == findParent(parent, targetGroup2);
}
void uniteGroup(int[] parent, int targetGroup1, int targetGroup2) {
parent[findParent(parent, targetGroup2)] = findParent(parent, targetGroup1);
}
public int solution(int[][] land, int height) {
int[] dx = new int[] { 0, 1, 0, -1 };
int[] dy = new int[] { 1, 0, -1, 0 };
int[][] group = new int[land.length][land.length];
int groupNumber = 0;
Deque<int[]> d = new ArrayDeque<>();
for (int i = 0; i < land.length; i++) {
for (int j = 0; j < land.length; j++) {
groupNumber++;
if (group[i][j] > 0) {
continue;
}
d.add(new int[] { i, j });
group[i][j] = groupNumber;
while (!d.isEmpty()) {
int[] target = d.pop();
for (int k = 0; k < 4; k++) {
int temp_x = target[0] + dx[k];
int temp_y = target[1] + dy[k];
if (temp_x < 0 || temp_x >= land.length || temp_y < 0 || temp_y >= land.length) {
continue;
}
if (group[temp_x][temp_y] > 0) {
continue;
}
if (Math.abs(land[target[0]][target[1]] - land[temp_x][temp_y]) > height) {
continue;
}
group[temp_x][temp_y] = groupNumber;
d.add(new int[] { temp_x, temp_y });
}
}
}
}
List<Edge> e = new ArrayList();
for (int i = 0; i < land.length; i++) {
for (int j = 0; j < land.length; j++) {
for (int k = 0; k < 4; k++) {
int temp_x = i + dx[k];
int temp_y = j + dy[k];
if (temp_x < 0 || temp_x >= land.length || temp_y < 0 || temp_y >= land.length) {
continue;
}
if (group[temp_x][temp_y] == group[i][j]) {
continue;
}
e.add(new Edge(Math.abs(land[i][j] - land[temp_x][temp_y]),
new int[] { group[i][j], group[temp_x][temp_y] }));
}
}
}
int answer = 0;
int[] parent = new int[groupNumber + 1];
Collections.sort(e);
for (int i = 1; i < groupNumber + 1; i++) {
parent[i] = i;
}
for (int i = 0; i < e.size(); i++) {
int cost = e.get(i).getCost();
int fromGroup = e.get(i).getEdge()[0];
int toGroup = e.get(i).getEdge()[1];
if (!isSameParent(parent, fromGroup, toGroup)) {
uniteGroup(parent, fromGroup, toGroup);
answer += cost;
}
}
return answer;
}
}
참고한 글
- https://yabmoons.tistory.com/470
Leave a comment