사이클이 없는 그래프에서 노드의 순서를 찾는 알고리즘





위처럼 이제 다시 큐에서 정점 2를 빼내주고 새롭게 3은 정점이 0이 될것이다. 이러한 과정을 반복해서 모두 큐에서 원소를 뺸 순서대로 나열한 것이 위상정렬이 된것이다.


위 그래프 형태처럼 방향은 존재하고 사이클은 존재하지 않는 그래프를 위상정렬을 통해 값을 산출해내는 코드입니다.
import java.io.*;
import java.util.*;
public class SWEA_1267 {
static int ans, V, E;
static List<Integer>[] graph;
static int[] inDegree;
static List<Integer> result;
public static void main(String[] args) throws Exception {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringBuilder sb = new StringBuilder();
for (int k = 1; k <= 10; k++) {
StringTokenizer st = new StringTokenizer(br.readLine());
V = Integer.parseInt(st.nextToken());
E = Integer.parseInt(st.nextToken());
graph = new ArrayList[V + 1];
for (int i = 1; i <= V; i++) {
graph[i] = new ArrayList<Integer>();
}
result = new ArrayList<Integer>();
inDegree = new int[V + 1]; // 진입 차수 저장용
st = new StringTokenizer(br.readLine());
for (int i = 0; i < E ; i++) {
int a = Integer.parseInt(st.nextToken());
int b = Integer.parseInt(st.nextToken());
graph[a].add(b);
inDegree[b]++; // b에 들어오는 진입 차수가 추가되었으니 증가
}
topology();
sb.append("#").append(k).append(" ");
for (int i = 0; i < V; i++) {
sb.append(result.get(i)).append(" ");
}
sb.append("\n");
}
System.out.println(sb);
}
static void topology() {
Queue<Integer> q = new LinkedList<Integer>();
for (int i = 1; i <= V; i++) {
if (inDegree[i] == 0) {
q.add(i); // 일단 진입차수 0인 애들 먼저 넣고
}
}
while (!q.isEmpty()) {
int temp = q.poll();
result.add(temp);
for (int i = 0; i < graph[temp].size(); i++) {
inDegree[graph[temp].get(i)] -= 1; // 해당 노드랑 연결된 하위 노드들의 진입차수를 1 빼주고
if (inDegree[graph[temp].get(i)] == 0) {
q.add(graph[temp].get(i)); // 만약 진입차수 -1 했는데 0이면 q에 넣고
}
}
}
}
}