1. ๋ฌธ์ ์ค๋ช ๐
์ ์ 1 โ ์ ์ N์ผ๋ก ๊ฐ ๊ฑด๋ฐ, ์ด ๋ ์ฌ์ด์ ํน์ ํ ์ ์ A
, B
๋ฅผ ๊ผญ ๊ฑฐ์ณ์ผ ํ๋ค. ์ด ํน์ ํ ์ ์ 2๊ฐ๋ฅผ ๊ผญ ๊ฑฐ์น๋ฉด์ ๊ฐ ์ ์๋ ์ต๋จ ๊ฒฝ๋ก์ ๋น์ฉ์ ๊ตฌํ์ฌ๋ผ
2. ๊ตฌํ ๋ฐฉ๋ฒ ๐๏ธ
KEY WORD
: DIJKSTRA
ํน์ ์ ์ A
,B
๋ฅผ ๊ผญ ๊ฑฐ์น๋ฉด์, 1 โ N ๊น์ง ๊ฐ๋ ์ต๋จ ๊ฒฝ๋ก๋ ๋ค์ 2๊ฐ์ง ์ค ํ๋ ์ผ ๊ฒ์ด๋ค.
1
โA
,A
โB
,B
โN
๊ฐ๊ฐ์ ์ต๋จ ๊ฒฝ๋ก๋ฅผ ๊ตฌํด์ ํฉํ๋ค.1
โB
,B
โA
,A
โN
๊ฐ๊ฐ์ ์ต๋จ ๊ฒฝ๋ก๋ฅผ ๊ตฌํด์ ํฉํ๋ค.
์ด๊ฒ ๊ฐ๋ฅํ ์ด์ ๋ ๋ชจ๋ ๊ฐ์ค์น๊ฐ ์์์ด๊ธฐ ๋๋ฌธ์ด๋ค. A
,B
๋ก ๊ฐ๋ ๋ถ๋ถ์ ์ธ ์ต๋จ ๊ฒฝ๋ก์์ ๋ฒ์ด๋๋ ์ ์ ์ ๋ฐฉ๋ฌธํ๋ ๊ฒ ์์ฒด๊ฐ ๋น์ฉ์ ๋๋ฆด ๋ฟ ๋์๋์ง ์๋๋ค. ๋ฐ๋ผ์ ๊ฐ๊ฐ ๋ถ๋ถ์ ์ธ ์ต๋จ ๊ฒฝ๋ก์ ํฉ์ด ๊ณง ์ ์ฒด ์ต๋จ ๊ฒฝ๋ก๊ฐ ๋ ์ ์๋ค. ๋ฐ๋ผ์ 1
, A
, B
๊ฐ๊ฐ์ ์ถ๋ฐ์ ์ผ๋ก ์ก๊ณ ๋ค์ต์คํธ๋ผ๋ฅผ ์งํํ์ฌ ์ ๊ธฐ์ ์ ์๋ ๋ถ๋ถ์ ์ธ ์ต๋จ ๊ฒฝ๋ก๋ฅผ ์ฐพ๋๋ค.
- 0๏ธโฃ ์ต๋จ ๊ฑฐ๋ฆฌ ๋ฐฐ์ด 3๊ฐ(๊ฐ๊ฐ
dist[0], dist[1], dist[2]
) ๋ง๋ค๊ธฐ, ์ธ์ ๋ฆฌ์คํธ ๋ง๋ค๊ธฐ - 1๏ธโฃ
1
,A
,B
๋ฅผ ์์์ ์ผ๋ก๋ค์ต์คํธ๋ผ
๋ฅผ ๋๋ ค์ ๊ฐ๊ฐ์ ์ต๋จ ๊ฑฐ๋ฆฌ ๋ฐฐ์ด์ ์์ฑ ์ํจ๋ค. - 2๏ธโฃ ์์์ ์ค๋ช ํ ์ต๋จ ๊ฒฝ๋ก๊ฐ ๋ ์ ์๋ ํ๋ณด์ง 2๊ฐ(์ดํ ans1, ans2) ๋ฅผ ์์ฑ์ํจ๋ค. (long์ผ๋ก ๋ง๋ ๋ค.)
- 3๏ธโฃ ๋ง์ฝ ํ๋ณด์ง์ ๋ต์ด
Integer.MAX_VALUE
๋ฅผ ๋๋๋ค๋ฉด, ๋ถ๋ถ์ ์ธ ๊ฒฝ๋ก ์ค ์ต์ ํ ๊ณณ์ ๊ทธ ์ฌ์ด์ ๊ฒฝ๋ก๊ฐ ์์ด์ ๋๋ฌํ ์ ์๋ค๋ ๋ป์ด๋ค. - 4๏ธโฃ๋ง์ฝ ํ๋ณด์ง ๋ ๋ค
Integer.MAX_VALUE
๋ฅผ ๋๋๋ค๋ฉด ๋ต์ผ๋ก-1
์ ์ถ๋ ฅํ๋ค. - 5๏ธโฃ์๋๋ฉด ๋ ์ฌ์ด์ ์ต๋จ ๊ฒฝ๋ก๋ฅผ ์ถ๋ ฅํ๋ค.
(1) ์๊ฐ๋ณต์ก๋ ๋ถ์ ๐
์ ์ ์ ๊ฐ์๋ฅผ N
, ๊ฐ์ ์ ๊ฐ์๋ฅผ E
๋ผ๊ณ ํ ๋, ๋ค์ต์คํธ๋ผ 3๋ฒ ๋๋ ค์ผ ํจ.
$O(3 E \log N)$
3. ์ฝ๋ ์๊ฐ ๐
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Comparator;
import java.util.PriorityQueue;
import java.util.StringTokenizer;
public class Main {
static class Node {
int i;
int w;
public Node (int i, int w) {
this.i = i;
this.w = w;
}
}
static class Dist {
int idx;
int dist;
public Dist (int idx, int dist) {
this.idx = idx;
this.dist = dist;
}
}
static int N, E, A, B;
static ArrayList<Node>[] lists;
static int iter = 0;
static int [][] dists;
public static void main(String[] args) throws IOException {
// ์
๋ ฅ
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st= new StringTokenizer(br.readLine());
N = Integer.parseInt(st.nextToken());
E = Integer.parseInt(st.nextToken());
lists = new ArrayList[N + 1];
dists = new int[3][N + 1];
for (int i = 1; i <= N; i++) {
lists[i] = new ArrayList<>();
}
for (int i = 0; i < E; i++) {
st = new StringTokenizer(br.readLine());
int start = Integer.parseInt(st.nextToken());
int end = Integer.parseInt(st.nextToken());
int weight = Integer.parseInt(st.nextToken());
lists[start].add(new Node(end, weight));
lists[end].add(new Node(start, weight));
}
st = new StringTokenizer(br.readLine());
A = Integer.parseInt(st.nextToken());
B = Integer.parseInt(st.nextToken());
// ๊ณ์ฐ
dijkstra(1);
dijkstra(A);
dijkstra(B);
long ans1 = (long)dists[0][A] + (long)dists[1][B] + (long)dists[2][N];
long ans2 = (long)dists[0][B] + (long)dists[2][A] + (long)dists[1][N];
// ์ถ๋ ฅ
System.out.println(Math.min(ans1, ans2) >= Integer.MAX_VALUE? -1 : Math.min(ans1,ans2));
}
public static void dijkstra(int start) {
int [] dist = find_dist(start);
Arrays.fill(dist, Integer.MAX_VALUE);
PriorityQueue<Dist> pq = new PriorityQueue<>(Comparator.comparingInt(o -> o.dist));
dist[start] = 0;
pq.add(new Dist(start, 0));
while (!pq.isEmpty()){
Dist now = pq.poll();
if(now.dist != dist[now.idx]) continue;
for (int i = 0; i < lists[now.idx].size(); i++) {
Node next = lists[now.idx].get(i);
if(dist[next.i] > dist[now.idx] + next.w) {
dist[next.i] = dist[now.idx] + next.w;
pq.add(new Dist(next.i, dist[next.i]));
}
}
}
}
public static int[] find_dist(int start){
return dists[iter++];
}
}
4. ๋ฐฐ์ด ๊ฒ๋ค ๐ฏ
82%์์ ํ๋ ธ๋ ์ด์ โจ
A
== 1
์ธ ๊ฒฝ์ฐ์ B
== N
์ธ ๊ฒฝ์ฐ๋ฅผ ์๊ฐํ์ง ๋ชปํ๋ค. ์ฒ์์ find_dist
ํจ์ ๋ชจ์์ ๋ค์๊ณผ ๊ฐ์๋ค.
public static int[] find_dist(int start){
if(start == 1) return dists[0];
else if (start == A) return dists[1];
else return dists[2];
}
์ด๋ฌ๋ฉด A
== 1
์ด์์ ๋, ์ด๋ฏธ ๊ณ์ฐ์ด ๋๋ dist[0]
๋ฅผ ์ด๊ธฐ๊ฐ์ผ๋ก ์๊ฐํด์ ํ๋ฒ ๋ ๊ณ์ฐ์ ํด๋ฒ๋ ค์ ๋ต์ด ํ์ด์ ธ ๋ฒ๋ฆฐ๋ค.
์ด๋ฅผ ๊ณ ์น๋ ํด๊ฒฐ ๋์๋ค.
๋ต ์๋ฃํ์ long
์ผ๋ก ๋ฐ๊พธ์ด์ ๊ฐ๋
์ฑ ๋์ด๊ธฐ
์์์ ์ค๋ช
ํ๋ฏ์ด, ์ฌ์ฉํด์ผํ๋ ์ ์ ๋ค ์ฌ์ด์ ๊ฐ์ ์ด ์์ด์ ๊ฐ์ง ๋ชปํ๋ ๊ฒฝ์ฐ Integer.MAX_VALUE
๊ฐ ๊ณ์ฐ์ ๋ํด์ง๋ค. ์ด๋ ans1
์ด๋ ans2
์ ์๋ฃํ์ด int
์ด๋ฉด overflow๊ฐ ๋์ -๊ฐ์ผ๋ก ๋ฐ๋๊ณ ๊ฒฐ๊ณผ๊ฐ ์ด์ํด์ง๋ค. ๊ฐ ์ ์ ๋ค ์ฌ์ด ๊ฐ์ค์น๊ฐ ์์ ๋ ๋ง๋ค if ์กฐ๊ฑด์ ๊ฑธ์ด ์ฒ๋ฆฌํ๋ ค๋, ๋์น๋ ๋ถ๋ถ๋ ๋ง์๊ณ , ๊ฐ๋
์ฑ์ด ๋จ์ด์ก๋ค.
// ์ฒซ ์ฝ๋
int ans0 = -1;
int ans1 = dists[0][A] + dists[1][B] + dists[2][N];
int ans2 = dists[0][B] + dists[2][A] + dists[1][N];
if(1 == A){
ans0 = dists[1][B] + dists[2][N];
if(B== N){
ans0 = dists[0][N];
}
}else if (B == N) {
ans0 = dists[0][A] + dists[1][N];
}else if (dists[0][A] == Integer.MAX_VALUE || dists[2][N] == Integer.MAX_VALUE){
ans0 = ans2;
if(dists[0][B] == Integer.MAX_VALUE || dists[1][N] == Integer.MAX_VALUE) {
ans0 = -1;
}
}else if (dists[0][B] == Integer.MAX_VALUE || dists[1][N] == Integer.MAX_VALUE){
ans0 = ans1;
}
System.out.println(ans0);
์ด ๋๋ฌธ์ ํ๋ ค์, ans1
๊ณผ ans2
์ ์๋ฃํ์ long
์ผ๋ก ๋ฐ๊พธ์ด์ ์ดํฉ์ด Integer.MAX_VALUE
๋ณด๋ค ๋์ผ๋ฉด ๊ทธ ์ฌ์ด ์ต์ ํ๋์ ๊ตฌ๊ฐ์ ๋๋ฌํ ์ ์์์ ์ ์ ์๊ฒ ์ฝ๋๋ฅผ ๋ฐ๊พธ์ด ๊ฐ๋
์ฑ์ ๋ํ๋ค.
// ๋ฐ๊พผ ํ ์ฝ๋
long ans1 = (long)dists[0][A] + (long)dists[1][B] + (long)dists[2][N];
long ans2 = (long)dists[0][B] + (long)dists[2][A] + (long)dists[1][N];
// ์ถ๋ ฅ
System.out.println(Math.min(ans1, ans2) >= Integer.MAX_VALUE? -1 : Math.min(ans1,ans2));