BOJ_1005_ACM Craft_java

2023. 2. 5. 22:05Algorithm/BOJ

728x90

https://www.acmicpc.net/problem/1005

 

1005번: ACM Craft

첫째 줄에는 테스트케이스의 개수 T가 주어진다. 각 테스트 케이스는 다음과 같이 주어진다. 첫째 줄에 건물의 개수 N과 건물간의 건설순서 규칙의 총 개수 K이 주어진다. (건물의 번호는 1번부

www.acmicpc.net

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.*;

/**
 백준 1005번 ACM Craft
 골드 3
 */
public class BOJ_1005_ACM_Craft {
    public static void main(String[] args) throws IOException {
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        StringTokenizer st;
        StringBuilder sb = new StringBuilder();

        int T = Integer.parseInt(br.readLine()); // 테스트 케이스
        for (int tc = 1; tc<=T; tc++){
            st = new StringTokenizer(br.readLine());
            int N = Integer.parseInt(st.nextToken()); // 건물 수
            int K = Integer.parseInt(st.nextToken()); // 건물 건설 순서 규칙
            int[] inDegree = new int[N+1]; // 노드 진입 차수
            List<Integer>[] edges = new List[N+1]; // 간선 정보
            for (int i = 1; i<=N; i++){ // 간선 정보 초기화
                edges[i] = new ArrayList<>();
            }
            int[] dp = new int[N+1]; // 노드 도달 비용 dp 배열
            int[] D = new int[N+1]; // 건물 건설 시간
            st = new StringTokenizer(br.readLine());
            for (int i = 1; i<=N; i++){
                D[i] = Integer.parseInt(st.nextToken());
            }

            for (int i = 0; i<K; i++){ // 건설 순서 규칙
                st = new StringTokenizer(br.readLine());
                int before = Integer.parseInt(st.nextToken());
                int after = Integer.parseInt(st.nextToken());
                edges[before].add(after);
                inDegree[after]++;
            }

            int W = Integer.parseInt(br.readLine()); // 목표 건물 번호

            // 위상정렬
            Queue<Integer> queue = new LinkedList<>();
            boolean flag = false; // 중간 종료용 flag
            for (int i = 1; i<=N; i++){
                if (inDegree[i] == 0){
                    queue.offer(i); // 시작 노드
                    dp[i] = D[i];
                    while (!queue.isEmpty()){
                        int node = queue.poll();
                        if (node == W){ // 목표 건물
                            sb.append(dp[node]).append("\n");
                            flag = true;
                            break;
                        }
                        inDegree[node] = -1;
                        for (int next : edges[node]){
                            inDegree[next]--;
                            dp[next] = Math.max(dp[next], dp[node] + D[next]); // 이전 건물 모두 건설이 완료되어야함 -> max
                            if (inDegree[next] == 0){
                                queue.offer(next);
                            }
                        }
                    }
                    if (flag) break;
                }
            }
        }

        System.out.println(sb.toString());
    }
}

'Algorithm > BOJ' 카테고리의 다른 글

BOJ_2473_세 용액_java  (0) 2023.02.07
BOJ_2623_음악프로그램_java  (0) 2023.02.05
BOJ_2252_줄 세우기_java  (0) 2023.02.05
BOJ_2143_두 배열의 합  (0) 2023.02.02
BOJ_20040_사이클게임_java  (0) 2023.01.30