아이디어
- 최단거리 테이블 초기화 - 시작점 :0, 나머지 : 무한
- 힙에 (0, 시작점) 추가
- 힙이 빌 때까지 최단 거리 테이블 갱신
- 힙에서 가장 비용이 적은 원소를 선택
- 비용이 최단 거리 테이블의 값과 같은지 확인 → 다르면, 쓸모없는 원소이므로 6번 skip
- 뽑은 요소와 이웃한 정점의 최단거리를 갱신
어려운점 & 실수
서로 다른 두 정점 사이에 여러 개의 간선이 존재할 수도 있음에 유의한다.
→ 굳이 신경써서 graph를 채우지 않아도, 다익스트라 알고리즘 돌면서 걸러진다.- 입력 실수
간선 입력받는 반복문 조건을 잘못줬었다...ㅎ ㅠ
for (int i = 1; i < graph.length; i++) {
→
for (int i = 0; i < E; i++) {
정답
importjava.io.BufferedReader;
importjava.io.IOException;
importjava.io.InputStreamReader;
importjava.util.*;
publicclassN1753 {
publicstaticvoidmain(String[] args) throwsIOException {
BufferedReaderbr = newBufferedReader(newInputStreamReader(System.in));
StringTokenizertoken = newStringTokenizer(br.readLine());
intV = Integer.parseInt(token.nextToken());
intE = Integer.parseInt(token.nextToken());
intstart = Integer.parseInt(br.readLine());
//서로 다른 두 정점 사이에 여러 개의 간선이 존재할 수도 있음에 유의한다.//가장 짧은 간선만 저장하도록 HashMap에 (목적지, Node) 저장LinkedList<Node>[] graph = newLinkedList[V + 1];
for (inti = 0; i < graph.length; i++) {
graph[i] = newLinkedList<>();
}
for (inti = 0; i < E; i++) {
token = newStringTokenizer(br.readLine());
intfrom = Integer.parseInt(token.nextToken());
intto = Integer.parseInt(token.nextToken());
intcost = Integer.parseInt(token.nextToken());
// 방향 연결 그래프LinkedList<Node> nodes = graph[from];
nodes.add(newNode(cost, to));
}
//최단 거리 테이블 초기화 - 시작점 : 0, 나머지 : 무한int[] D = newint[V + 1];
intINF = 100_000_0001;
Arrays.fill(D, INF);
D[start] = 0;
PriorityQueue<Node> queue = newPriorityQueue<>();
//1. (0, 시작점) 힙에 추가queue.add(newNode(0, start));
//힙이 빌때까지 최단거리 테이블 갱신while (!queue.isEmpty()) {
// 2. 힙에서 가장 거리가 작은 원소를 선택Nodecur = queue.poll();
// 3. 거리값이 최단 거리 테이블의 값과 같은지 확인if (cur.cost != D[cur.to]) { //쓸모없는 원소이므로 skipcontinue;
}
// 4. 뽑은 요소와 이웃한 정점의 최단거리를 갱신LinkedList<Node> nodes = graph[cur.to];
for (Nodenode : nodes) {
intnewCost = node.cost + cur.cost;
if (newCost < D[node.to]) {
D[node.to] = newCost;
queue.add(newNode(D[node.to], node.to));
}
}
}
//출력StringBuildersb = newStringBuilder();
Arrays.stream(D).skip(1).forEach(n -> {
if (n == INF) {
sb.append("INF").append("\n");
return;
}
sb.append(n).append("\n");
});
System.out.println(sb.toString());
}
staticclassNodeimplementsComparable<Node> {
intcost;
intto;
publicNode(finalintcost, finalintto) {
this.cost = cost;
this.to = to;
}
@OverridepublicintcompareTo(finalNodeo) {
returnthis.cost - o.cost;
}
}
}
아이디어
어려운점 & 실수
서로 다른 두 정점 사이에 여러 개의 간선이 존재할 수도 있음에 유의한다.→ 굳이 신경써서 graph를 채우지 않아도, 다익스트라 알고리즘 돌면서 걸러진다.
간선 입력받는 반복문 조건을 잘못줬었다...ㅎ ㅠ
for (int i = 1; i < graph.length; i++) {→
for (int i = 0; i < E; i++) {정답