207. 课程表


package leetcode.top100;

import java.util.*;

public class Timetable {


    public static boolean canFinish(int numCourses, int[][] prerequisites) {
        /**
         * 核心思想是用类似广度优先遍历
         * 1.先遍历prerequisites数组,计算入度。
         *
         */

        // 1.计算课程号和其对应节点的入度
        HashMap<Integer, Integer> inDegree = new HashMap<>();
        // 将课程放入
        for (int i = 0; i < numCourses; i++) {
            inDegree.put(i,0);
        }

        //2.依赖关系。存储依赖关系
        HashMap<Integer, List<Integer>> adj = new HashMap<>();


        // 初始化入度和依赖关系  a.算出每个节点的入度。 b.算出每个节点是谁的上个节点,也就是谁的先修课
        for (int[] relate : prerequisites){
            // (3,0), 想学3号课程要先完成0号课程, 更新3号课程的入度和0号课程的依赖(邻接表)
            int cur = relate[0];
            int before = relate[1];
            // (1).更新入度
            inDegree.put(cur,inDegree.get(cur)+1);
            // 2.当前节点的邻接表
            if (!adj.containsKey(before)){
                adj.put(before,new ArrayList<>());
            }
            adj.get(before).add(cur);
        }

        // 3.BFS, 将入度为0的课程放入队列, 队列中的课程就是没有先修, 可以学的课程
        Queue<Integer> queue = new LinkedList<>();
        for (int key:inDegree.keySet()){
            if (inDegree.get(key)==0){
                queue.add(key);
            }
        }

        // 取出一个节点, 对应学习这门课程.
        // 遍历当前邻接表, 更新其入度; 更新之后查看入度, 如果为0, 加入到队列
        while (!queue.isEmpty()){
            Integer cur = queue.poll();
            // 遍历当前课程的邻接表, 更新后继节点的入度
            if (!adj.containsKey(cur)){
                continue;
            }
            // 当前节点代表课程是哪些课程先修课
            List<Integer> impactList = adj.get(cur);
            for (int k:impactList){
                inDegree.put(k,inDegree.get(k)-1);
                if (inDegree.get(k)==0){
                    queue.add(k);
                }
            }

        }

        // 4.遍历入队, 如果还有课程的入度不为0, 返回fasle
        for (int key:inDegree.keySet()){
            if (inDegree.get(key)!=0){
                return false;
            }
        }

        return true;
    }

    public static void main(String[] args) {
        int[][] course = new int[][]{
                {1,0}
        };
        boolean res = canFinish(6, course);
        System.out.println(res);
    }
}

转载评论:https://leetcode.cn/problems/course-schedule/solutions/250377/bao-mu-shi-ti-jie-shou-ba-shou-da-tong-tuo-bu-pai-/

作者:静默虚空
欢迎任何形式的转载,但请务必注明出处。
限于本人水平,如果文章和代码有表述不当之处,还请不吝赐教。

posted @   Chenyi_li  阅读(4)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· .NET10 - 预览版1新功能体验(一)
历史上的今天:
2022-05-15 idea 解决查看源码没有注释
点击右上角即可分享
微信分享提示