当前位置: 首页 > news >正文

LeetCode热题--207. 课程表--中等

1. 题目

你这个学期必须选修 numCourses 门课程,记为 0 到 numCourses - 1 。

在选修某些课程之前需要一些先修课程。 先修课程按数组 prerequisites 给出,其中 prerequisites[i] = [ai, bi] ,表示如果要学习课程 ai 则 必须 先学习课程 bi 。

例如,先修课程对 [0, 1] 表示:想要学习课程 0 ,你需要先完成课程 1 。
请你判断是否可能完成所有课程的学习?如果可以,返回 true ;否则,返回 false 。

示例 1:
输入:numCourses = 2, prerequisites = [[1,0]]
输出:true
解释:总共有 2 门课程。学习课程 1 之前,你需要完成课程 0 。这是可能的。

示例 2:
输入:numCourses = 2, prerequisites = [[1,0],[0,1]]
输出:false
解释:总共有 2 门课程。学习课程 1 之前,你需要先完成​课程 0 ;并且学习课程 0 之前,你还应先完成课程 1 。这是不可能的。

2. 题解

class Solution {public boolean canFinish(int numCourses, int[][] prerequisites) {// 入度数组,用于记录每门课程的入度int[] inDegree = new int[numCourses];// 邻接表,存储每门课程的后续课程List<List<Integer>> adjList = new ArrayList<>();for (int i = 0; i < numCourses; i++) {adjList.add(new ArrayList<>());}// 计算每门课程的入度,并构建邻接表for (int[] prerequisite : prerequisites) {int course = prerequisite[0];int preCourse = prerequisite[1];inDegree[course]++;adjList.get(preCourse).add(course);}// 存储入度为 0 的课程的队列Queue<Integer> queue = new LinkedList<>();for (int i = 0; i < numCourses; i++) {if (inDegree[i] == 0) {queue.offer(i);}}// 记录已完成课程的数量int count = 0;while (!queue.isEmpty()) {int selectedCourse = queue.poll();count++;// 获取当前课程的后续课程列表List<Integer> nextCourses = adjList.get(selectedCourse);for (int nextCourse : nextCourses) {// 后续课程的入度减 1inDegree[nextCourse]--;if (inDegree[nextCourse] == 0) {queue.offer(nextCourse);}}}// 如果已完成课程的数量等于总课程数,则可以完成所有课程return count == numCourses;}
}

3. 解析

出自:「图解」拓扑排序 | 课程表问题

int[] inDegree = new int[numCourses];: 初始化一个数组来记录每门课程的入度,表示从其他课程到当前课程的箭头数量。

List<List> adjList = new ArrayList<>();: 创建一个邻接表(Adjacency List)用于存储每门课程的后续课程。这是一个列表的列表,其中每个内部列表表示一门课程及其所有的后续课程。
for (int i = 0; i < numCourses; i++) { adjList.add(new ArrayList<>()); }: 初始化邻接表中的空列表以匹配每门课程的数量。

4-7: 遍历所有预备课程,计算每个课程的入度并构建邻接表。对于每一对预备课程(preCourse, course),将course的入度加1,并将preCourse添加到course的后续课程列表中。
Queue queue = new LinkedList<>();: 创建一个队列来存储所有入度为0的课程。这是因为这些课程没有先决条件(即它们是可以直接选修的课程)。

9-15: 遍历所有的课程,将那些入度为0的课程添加到队列中。
int count = 0;: 初始化一个计数器来记录已经完成的课程数量。

17-24: 开始主循环,直到队列为空(即没有任何可以选择的课程了)或者已完成的课程数量等于总课程数(表示所有课程都可以完成)。在每一轮中,从队列中取出一门课程进行处理(增加计数器并将其后续课程的入度减1),如果任何一个后续课程的入度降为0(即没有先决条件了),就将它添加到队列中。

25: 最后返回已完成课程数量是否等于总课程数来判断能否完成所有课程。
这段代码是拓扑排序的一种实现方式,用于解决课程表问题(Schedule of Courses),如果能通过所有的入度为0的课程,那么就可以完成所有课程。

http://www.dtcms.com/a/422742.html

相关文章:

  • 算法奇妙屋(四)-归并分治
  • 【嵌入式硬件实例】-晶体管放大器
  • ArcGIS数据迁移问题汇总(postgresql)
  • SQLyog:一款功能强大、简单易用的MySQL管理工具
  • Boost 搜索引擎
  • 紧跟大数据技术趋势:食物口味分析系统Spark SQL+HDFS最新架构实现
  • c2c网站的建设做企业网站有哪些好处
  • 从AI角度深入解析和论述哲学的终极答案‘语言即世界‘
  • 网站开发实训报告织梦手机网站建设
  • python做网站开发免费公司企业建站代理
  • 科技信息差(9.29)
  • ES如何基于Linux配置开机自启动
  • DeepSeek Java 单例模式详解
  • 单例模式入门
  • PMON failed to acquire latch 的报错及sqlplus / as sysdba 无法连接
  • Vibe Coding - MCP Feedback Enhanced(交互反馈 MCP)
  • Elasticsearch 搭建(亲测)
  • Java 设计模式在 Spring 框架中的实践:工厂模式与单例模式
  • 手机网站被禁止访问怎么打开网页软件应用大全
  • SQL注入与防御:从攻击原理到预编译防御
  • 【MySQL】Oracle与MySQL,跨库数据转储
  • 营销型网站建设的步骤附近公司
  • 【Java】网络编程(5)
  • 实现VLAN间通信
  • OSPF 和 IS-IS的路由过滤对比
  • Eclipse 透视图(Perspective)
  • 【Linux操作系统】简学深悟启示录:动静态库
  • 网站搭建设计筑龙网怎么免费下载
  • 网站制作哪家好网站建设中期目标
  • 前端开发时npm install报错解决方案