[SWEA] 1251. 하나로
문제
풀이
MST 중 프림 알고리즘을 사용함.
섬의 위치(x,y)로 주어졌기 때문에 섬 간의 거리를 직접 비용을 계산했다.
그리고 인접한 섬들 중 비용이 가장 적은 섬을 찾기 위해서 PriorityQueue를 사용해주었다. 현재 섬의 방문 여부를 체크하고 방문하지 않은 섬이라면 방문처리 후 최소비용에 값을 누적했다. 그리고 현재 위치에 인접한 섬들 중 방문하지 않은 섬들을 모두 PriorityQueue에 대입해주었고 이를 반복하다가 PriorityQueue가 비거나 cnt의 갯수가 N이라면 while문을 종료했다.
JAVA코드
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.PriorityQueue;
import java.util.StringTokenizer;
public class SWEA_하나로 {
static int N; // 섬의 개수
static long[] xPoint;
static long[] yPoint;
static class Edge implements Comparable<Edge> {
int to;
long cost;
public Edge(int to, long cost) {
super();
this.to = to;
this.cost = cost;
}
@Override
public int compareTo(Edge o) {
return Long.compare(this.cost, o.cost);
}
}
static LinkedList<ArrayList<Edge>> adj; // 인접배열
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st = new StringTokenizer(br.readLine());
int TC = Integer.parseInt(st.nextToken());
for (int tc = 1; tc <= TC; tc++) {
N = Integer.parseInt(br.readLine());
xPoint = new long[N];
yPoint = new long[N];
adj = new LinkedList<>();
for(int i=0;i<N;i++) {
adj.add(new ArrayList<>());
}
st = new StringTokenizer(br.readLine());
for (int i = 0; i < N; i++) {
xPoint[i] = Long.parseLong(st.nextToken());
}
st = new StringTokenizer(br.readLine());
for (int i = 0; i < N; i++) {
yPoint[i] = Long.parseLong(st.nextToken());
}
double E = Double.parseDouble(br.readLine());
for (int i = 0; i < N; i++) {
for (int j = 0; j < N; j++) {
if (i != j) {
long distance = (xPoint[i] - xPoint[j]) * (xPoint[i] - xPoint[j])
+ (yPoint[i] - yPoint[j]) * (yPoint[i] - yPoint[j]);
adj.get(i).add(new Edge(j, distance));
}
}
}
long result = mst();
double ans = result*E;
System.out.println("#"+tc+" "+Math.round(ans));
}
}
public static long mst() {
PriorityQueue<Edge> pq = new PriorityQueue<Edge>();
boolean[] visited = new boolean[N];
int cnt = 0;
long result = 0;
pq.offer(new Edge(0, 0));
while (!pq.isEmpty()) {
Edge current = pq.poll();
// 방문하지 않은 최소정점 찾기
if (visited[current.to])
continue;
visited[current.to] = true; // 방문처리
result += current.cost; // 누적비용
// cnt의 개수가 N이라면 break!
if (++cnt == N)
break;
for (Edge next : adj.get(current.to)) {
if (!visited[next.to]) {
pq.add(next);
}
}
}
return result;
}
}
Author And Source
이 문제에 관하여([SWEA] 1251. 하나로), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://velog.io/@jsw7000/SWEA-1251.-하나로저자 귀속: 원작자 정보가 원작자 URL에 포함되어 있으며 저작권은 원작자 소유입니다.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)