1. ๋ฌธ์ ์ ๋ํ์ฌ ๐ฆ
https://www.acmicpc.net/problem/2252
(1) ์กฐ๊ฑด ๋ถ์ ๐
ํค ์์๋ณ๋ก ํ์๋ค์ ์ ๋ ฌํ๋ ค ํ๋ค.
- ํค ์์์๋ ์ํ์ด ์กด์ฌํ ์ ์๋ค. (์ฌ์ดํด ์๋ ๊ทธ๋ํ)
- ํค์๋ ๋์๊ฐ ์กด์ฌํ๋ค. (๋ฐฉํฅ ๊ทธ๋ํ)
- ํค์ ๋์ ๊ด๊ณ๊ฐ ์ผ๋ถ๋ง ์กด์ฌํ๊ธฐ ๋๋ฌธ์, ๋ต์ด ์ฌ๋ฌ๊ฐ์ง์ธ ๊ฒฝ์ฐ ์๋ฌด๊ฑฐ๋ ์ถ๋ ฅํด๋ผ
2. ์ฝ๋๊ฐ ๋์ค๊ธฐ๊น์ง ๐ ๏ธ
KEY WORD
: ์์ ์ ๋ ฌ
์ด ๋ฌธ์ ๋ ์ ํ์ ์ธ ์์์ ๋ ฌ ๋ฌธ์ ์ด๋ค.
๋ง์ฝ ์์์ ๋ ฌ์ ๋ํ ์ดํด๊ฐ ๋ถ์กฑํ์ ๋ถ๋ค์ [์๊ณ ๋ฆฌ์ฆ] ์์์ ๋ ฌ, ๊ทธ๋ฆผ์ผ๋ก ์ฝ๊ฒ ์ค๋ช
^^์ ๋ณด๊ณ ์ค์๊ธธ ๋ฐ๋๋ค.
์ฒ์์๋ ๊ทธ์ ์ง์ ์ฐจ์ ๋ฐฐ์ด + for, while ๋ฐ๋ณต๋ฌธ์ผ๋ก ๋ฌธ์ ๋ฅผ ํ์๋๋ ์๊ฐ์ด 963ms ์ ๋๋ก ๋๊ฒ ๋์๋ค.
์ด๋ฅผ ์ต์ ํ ํ๋ ค๋ฉด ์ธ์ ๋ฆฌ์คํธ + BFS ๋ฐฉ์์ผ๋ก ๊ฐ์ฅ ์ ํ๋๋ ์์ ์ ์ฐพ๋ ๋ฐฉ๋ฒ์ ํ์ฉํด์ผํ๋ค. ์์ธํ ๋ฐฉ๋ฒ์ SUDO CODE์์ ๋งํ๋๋ก ํ๊ฒ ๋ค.
(1) ์๊ฐ๋ณต์ก๋ ๋ถ์ โณ
์ ์ ์ ๊ฐ์๋ฅผ $N$, ๊ฐ์ ์ ๊ฐ์๋ฅผ $M$ ์ด๋ผ๊ณ ํ ๋,
์์ ์ ๋ ฌ ์์ฒด๋ฅผ BFS ๋ก ๊ตฌํํ์์ผ๋ก ์ ์ฒด ์๊ฐ๋ณต์ก๋๋ $O(N +M)$ ์ด๋ค.
3. ์ฝ๋ ๐
(1) SUDO CODE ๐ฌ
+ 0. ์ธ์ ๋ฆฌ์คํธ ์์ฑ๊ณผ ๋์์ ์ง์
์ฐจ์ ๋ฐฐ์ด ๋ง๋ค๊ธฐ
+ 1. Queue์ ์ง์
์ฐจ์๊ฐ 0์ธ ์ ์ (๊ฐ์ฅ ์ ํ๋๋ ์ ์ )์ ๋ฃ๊ณ ํ ํฌ๊ธฐ๊ฐ 0์ด ๋ ๋๊น์ง ๋ค์์ ๋ฐ๋ณต
- (1) front์์ ์ ์ ๋ฒํธ๋ฅผ ํ๋ ๊บผ๋ธ๋ค.
- (2) ํด๋น ์ ์ ์ ์ง์
์ฐจ์ ๊ฐ์ 1 ์ค์ธ๋ค. (0์ ํ ์์ ๊ฐ์ฅ ์ ํ๋๋ ์์
, -1์ ์ด๋ฏธ ๋ฐฉ๋ฌธํ ์ง์ ์ ๋ปํจ)
- (3) ํด๋น ์ ์ ์์ ๋ฐฉ๋ฌธ ๊ฐ๋ฅํ ์ ์ ๋ค์ ์ง์
์ฐจ์๋ฅผ 1 ์ค์ธ๋ค.
- (4) ๋ง์ฝ (3)๋ฒ ์์
ํ ์ง์
์ฐจ์ = 0์ด ๋๋ ์ง์ ์ด ์๋ค๋ฉด ๋ค์ ์์ ์ ๊ฐ์ฅ ์ ํ๋์ด์ผํ ์์
์์ผ๋ก ํ์ ๋ฃ๋๋ค.
+ 2. ๋งค ํ ์ฝ์
ํ ๋๋ง๋ค ์ ๋ต์ ์ ์ ๋ฒํธ๋ฅผ ์ถ๊ฐํ๋ค.
+ (๊ฐ ์์ ์ ๊ฐ์ฅ ์ ํ๋์ด์ผํ ์์
๋ค์ ์ฐจ๋ก๋ก ์ ๋ต์ ๋ฃ์ด์ฃผ๋ฉด ๊ทธ๊ฒ์ด ๊ณง '์ ๋ ฌ๋ ์์'์ด๋ค.)
(2) JAVA CODE โ
import java.io.*;
import java.util.*;
public class Main{
static int N, M;
static ArrayList<Integer> [] lists;
static int [] inDegree;
public static void main(String[] args) throws IOException {
init();
topologicalSorting();
}
public static void init() throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st = new StringTokenizer(br.readLine());
N = Integer.parseInt(st.nextToken());
M = Integer.parseInt(st.nextToken());
lists= new ArrayList [N+1];
inDegree = new int [N+1];
for (int i = 1; i < N+1; i++) {
lists[i] = new ArrayList<>();
}
for (int i = 0; i < M; i++) {
st = new StringTokenizer(br.readLine());
int A = Integer.parseInt(st.nextToken());
int B = Integer.parseInt(st.nextToken());
lists[A].add(B);
inDegree[B]++;
}
}
public static void topologicalSorting(){
StringBuilder ans = new StringBuilder();
ArrayDeque<Integer> aq1 = new ArrayDeque<>();
for (int i = 1; i < N+1; i++) {
if(inDegree[i] == 0) {
aq1.add(i);
ans.append(i).append(" ");
}
}
while (!aq1.isEmpty()){
int now = aq1.poll();
for (int i = 0; i < lists[now].size(); i++) {
int next = lists[now].get(i);
inDegree[next]--;
if(inDegree[next] == 0) {
aq1.add(next);
ans.append(next).append(" ");
}
}
}
System.out.println(ans);
}
}
4. ํธ๋ฌ๋ธ ์ํ or ๋ฐฐ์ด ์ ๐
A. ์ธ์ ๋ฆฌ์คํธ ๊ธฐ๊ป ๋ง๋ค๊ณ for, while๋ฌธ์ผ๋ก ํ ์์ ๊ฐ์ฅ ์ ํ๋๋ ์์ ์ ์ฐพ์ ๊ฒ
๋ฐ์ ๊ฒ์ด for,while๋ฌธ์ผ๋ก ํผ ํ์ด์ธ๋ฐ,
- ๋ชจ๋ ์ ์ ์ด ๋ต์ด ์ ํ ๋๊น์ง, $O(N)$
- ๋งค ๋ฒ ํ์ฌ ๊ฐ์ฅ ์ ํ๋์ด์ผํ ์ ์ ์ฐพ๊ธฐ $O(N)$
- ํด๋น ์ ์ ๊ณผ ์ฐ๊ฒฐ๋ ์ ์ ๋ค ์ง์ ์ฐจ์ ์ค์ด๊ธฐ $O(M)$
1๋ฒ ๊ณผ์ ๋ด์ 2,3๋ฒ ๊ณผ์ ์ด ์์์ผ๋ก, ์ต์ข
์ ์ผ๋ก $O(N^2 + M)$์ด ๋๋ค.
๋ง์ฝ ๋ฌธ์ ์ ์ ํ์๊ฐ์ด 2์ด๊ฐ ์๋ 1์ด์๋ค๋ฉด ํด๋น ํ์ด๋ ํต๊ณผํ์ง ๋ชปํ์ ๋ฏ ์ถ๋ค.
import java.io.*;
import java.util.*;
public class Main{
static int N, M;
static ArrayList<Integer> [] lists;
static int [] inDegree;
static ArrayList<Integer> ans = new ArrayList<>();
public static void main(String[] args) throws IOException {
init();
topologicalSorting();
for(int temp : ans){
System.out.print(temp + " ");
}
}
public static void init() throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st = new StringTokenizer(br.readLine());
N = Integer.parseInt(st.nextToken());
M = Integer.parseInt(st.nextToken());
lists= new ArrayList [N+1];
inDegree = new int [N+1];
for (int i = 1; i < N+1; i++) {
lists[i] = new ArrayList<>();
}
for (int i = 0; i < M; i++) {
st = new StringTokenizer(br.readLine());
int A = Integer.parseInt(st.nextToken());
int B = Integer.parseInt(st.nextToken());
lists[A].add(B);
inDegree[B]++;
}
}
public static void topologicalSorting(){
while(ans.size() < N){
int now = 0;
for (int i = 1; i < N+1; i++) {
if(inDegree[i] == 0) {
inDegree[i]--;
now = i;
break;
}
}
ans.add(now);
for (int i = 0; i < lists[now].size(); i++) {
inDegree[lists[now].get(i)]--;
}
}
}
}