美文网首页
210. 课程表II(拓扑排序)

210. 课程表II(拓扑排序)

作者: 乘瓠散人 | 来源:发表于2021-04-18 11:43 被阅读0次

题目:总共有n门课需要选,一些课程存在先修课程,比如要想学习课程0,需要先修课程1。返回为了学完所有课程所安排的学习顺序,如果有多种正确的顺序,返回一种即可;否则返回空数组。
解析:拓扑排序的典型应用。

1. DFS

逆向思维,最先被放入栈中的节点是拓扑排序中最后面的节点。

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;

vector<vector<int>> edges;  //存储有向图
vector<int> visited;  //标记每个节点的状态:0=未搜索, 1=搜索中, 2=已完成
vector<int> result;  //用数组模拟栈, 0为栈底, n-1为栈顶
bool valid = true;  //判断有向图中是否有环

void dfs(int u){
    visited[u]=1;  //搜索中
    for(int v: edges[u]){
        if(visited[v] == 0){
            dfs(v);
            if(!valid) return;
        }else if(visited[v] == 1){  //搜索中 说明找到了环
            valid = false;
            return;
        }
    }
    visited[u]=2;  //已完成
    result.push_back(u);  //将该节点入栈
}

vector<int> findOrder(int numCourses, vector<vector<int>>& prerequisites){
    edges.resize(numCourses);
    visited.resize(numCourses);
    for(int i=0; i<prerequisites.size(); i++){
        edges[prerequisites[i][1]].push_back(prerequisites[i][0]);
    }
    //每次挑选一个<未搜索>的节点,开始进行深度优先搜索
    for(int i=0; i<numCourses; i++){
        if(visited[i]==0){
            dfs(i);
        }
        if(!valid) return {};
    }
    reverse(result.begin(), result.end());  //下标0为栈底,因此需要反序输出
    return result;
}

2. BFS

正向思维,按照入度为0的节点顺序生成拓扑排序。

#include <iostream>
#include <vector>
#include <queue>
#include <algorithm>
using namespace std;

vector<vector<int>> edges;  //存储有向图
vector<int> indeg;  //存储每个节点的入度 
vector<int> result; 

vector<int> findOrder(int numCourses, vector<vector<int>>& prerequisites){
    edges.resize(numCourses);
    indeg.resize(numCourses);
    for(int i=0; i<prerequisites.size(); i++){
        edges[prerequisites[i][1]].push_back(prerequisites[i][0]);
        indeg[prerequisites[i][0]]++;
    }
    queue<int> q;
    //将所有入度为0的节点放入队列
    for(int i=0; i<numCourses; i++){
        if(indeg[i] == 0){
            q.push(i);
        }
    }
    while(!q.empty()){
        int u = q.front();
        q.pop();
        result.push_back(u);
        for(int v: edges[u]){
            indeg[v]--;
            if(indeg[v]==0){
                q.push(v);
            }
        }
    }

    if(result.size() != numCourses) return {};
    return result;
}

相关文章

  • 210. 课程表II(拓扑排序)

    题目:总共有n门课需要选,一些课程存在先修课程,比如要想学习课程0,需要先修课程1。返回为了学完所有课程所安排的学...

  • 2022-04-14 拓扑排序 课程表

    210. 课程表 II[https://leetcode-cn.com/problems/course-sched...

  • 210. 课程表 II【拓扑排序】【BFS】【DFS】

    题目 代码BFS 代码DFS 思路:1、将入度为0的顶点m(及其关联边)从图G中取出,则剩余的G'依然是有向无环图...

  • 210.课程表II!

    本题跟207的区别在于除了判断图是否有环外,还让你输出拓扑排序的一个序列。207的时候一直没闹明白dfs跟拓扑排序...

  • 210. 课程表ii

    题目描述 现在你总共有 n 门课需要选,记为 0 到 n-1。在选修某些课程之前需要一些先修课程。 例如,想要学习...

  • 210. 课程表 II

    现在你总共有 n 门课需要选,记为 0 到 n-1。 在选修某些课程之前需要一些先修课程。 例如,想要学习课程 0...

  • Leetcode 存档点(1)-- 课程表II

    课程表II 这道题的基本思想是和拓扑排序相关联的,属于一个图的问题 图的存储结构 邻接矩阵表示法 邻接表表示法 拓...

  • 77. 组合/207. 课程表

    77. 组合 相关标签:回溯算法 207. 课程表 相关标签: DFS BFS 图 拓扑排序

  • Leetcode --- 课程表问题(拓扑排序)

    写在前:拓扑排序本质是BFS和贪心算法,是这两种算法在有向图应用的专有名词,即拓扑排序针对有向图问题。参考这里[h...

  • 利用DFS实现拓扑排序

    拓扑排序定义利用“DAG必有零入度顶点”的特性,实现拓扑排序基于DFS搜索的拓扑排序 1. 拓扑排序定义 将一个有...

网友评论

      本文标题:210. 课程表II(拓扑排序)

      本文链接:https://www.haomeiwen.com/subject/jtnmlltx.html