拓扑排序基础

拓扑排序用于解决有向无环图(DAG,Directed Acyclic Graph)按依赖关系排线性序列问题,直白地说解决这样的问题:有一组数据,其中一些数据依赖其他,问能否按依赖关系排序(被依赖的排在前面),或给出排序结果。

最常用解决拓扑排序问题的方法是Kahn算法,步骤可以概括为:

. 根据依赖关系,构建邻接矩阵或邻接表、入度数组
. 取入度为0的数据(即不依赖其他数据的数据),根据邻接矩阵/邻接表依次减小依赖其的数据的入度
. 判断减小后是否有新的入度为0的数据,继续进行第2步
. 直到所有数据入度为0、得到拓扑排序序列,或返回失败(存在环形依赖)

其中2、3两个步骤取入度为0数据、减小依赖其的数据的入度,过程像树的宽度优先搜索,用到类似BFS方法;以上过程用伪代码表示如下:

L ← Empty list that will contain the sorted elements
S ← Set of all nodes with no incoming edge
while S is non-empty do
    remove a node n from S
    add n to tail of L
    for each node m with an edge e from n to m do
        remove edge e from the graph
        if m has no other incoming edges then
            insert m into S
if graph has edges then
    return error   (graph has at least one cycle)
else
    return L   (a topologically sorted order)

下面看具体例子 207. Course Schedule (有n个课程,课程间有依赖关系,问能否完成所有课程):

    //207. Course Schedule
    bool canFinish(int numCourses, vector<pair<int, int>>& prerequisites) {        //构建邻接矩阵、入度数组
        vector<vector<int>> adj(numCourses);
        vector<);
        for(auto x:prerequisites){
            adj[x.second].push_back(x.first);
            indegree[x.first]++;
        }        //类似BFS
        queue<int> q;
        ;i<numCourses;i++)
            ) q.push(i);
        while(!q.empty()){
            int cur=q.front();
            q.pop();
            numCourses--;
            for(auto next:adj[cur])
                ) q.push(next);//新入度为0的先处理,这与正统BFS有区别
        }        //判断最后所有数据入度为0
        ;
    }

以上用到邻接矩阵(adjacency matrix)表示依赖关系,时间复杂度为O(V^2),其中V为数据个数。可视化过程:这里

相关LeetCode题:

207. Course Schedule  题解

210. Course Schedule II  题解

444. Sequence Reconstruction  题解

269. Alien Dictionary  题解

 
 
 

算法与数据结构基础 - 拓扑排序(Topological Sort)的更多相关文章

  1. LeetCode编程训练 - 拓扑排序(Topological Sort)

    拓扑排序基础 拓扑排序用于解决有向无环图(DAG,Directed Acyclic Graph)按依赖关系排线性序列问题,直白地说解决这样的问题:有一组数据,其中一些数据依赖其他,问能否按依赖关系排序 ...

  2. 【数据结构与算法Python版学习笔记】图——拓扑排序 Topological Sort

    概念 很多问题都可转化为图, 利用图算法解决 例如早餐吃薄煎饼的过程 制作松饼的难点在于知道先做哪一步.从图7-18可知,可以首先加热平底锅或者混合原材料.我们借助拓扑排序这种图算法来确定制作松饼的步 ...

  3. 拓扑排序 Topological Sort

    2018-05-02 16:26:07 在计算机科学领域,有向图的拓扑排序或拓扑排序是其顶点的线性排序,使得对于从顶点u到顶点v的每个有向边uv,u在排序中都在v前.例如,图形的顶点可以表示要执行的任 ...

  4. 算法与数据结构基础 - 广度优先搜索(BFS)

    BFS基础 广度优先搜索(Breadth First Search)用于按离始节点距离.由近到远渐次访问图的节点,可视化BFS 通常使用队列(queue)结构模拟BFS过程,关于queue见:算法与数 ...

  5. 算法与数据结构基础 - 图(Graph)

    图基础 图(Graph)应用广泛,程序中可用邻接表和邻接矩阵表示图.依据不同维度,图可以分为有向图/无向图.有权图/无权图.连通图/非连通图.循环图/非循环图,有向图中的顶点具有入度/出度的概念. 面 ...

  6. 算法与数据结构基础 - 分治法(Divide and Conquer)

    分治法基础 分治法(Divide and Conquer)顾名思义,思想核心是将问题拆分为子问题,对子问题求解.最终合并结果,分治法用伪代码表示如下: function f(input x size ...

  7. 算法与数据结构基础 - 贪心(Greedy)

    贪心基础 贪心(Greedy)常用于解决最优问题,以期通过某种策略获得一系列局部最优解.从而求得整体最优解. 贪心从局部最优角度考虑,只适用于具备无后效性的问题,即某个状态以前的过程不影响以后的状态. ...

  8. 算法与数据结构基础 - 数组(Array)

    数组基础 数组是最基础的数据结构,特点是O(1)时间读取任意下标元素,经常应用于排序(Sort).双指针(Two Pointers).二分查找(Binary Search).动态规划(DP)等算法.顺 ...

  9. 拓扑排序 (Topological Sorting)

    拓扑排序(Topological Sorting) 一.拓扑排序 含义 构造AOV网络全部顶点的拓扑有序序列的运算称为拓扑排序(Topological Sorting). 在图论中,拓扑排序(Topo ...

随机推荐

  1. easyui 使用jquery动态添加组件样式问题

    可以使用$.parser.parse();这个方法进行处理: 例如:   $.parser.parse(); 表示对整个页面重新渲染,渲染完就可以看到easyui原来的样式了:   var targe ...

  2. 关于安装了git或者小乌龟(TortoiseGit)使用之后出现红色! 绿色√ 蓝色?的解决办法:

    在当前目录中新建文件保存为(删除git信息.bat)在其写入:for /r . %%a in (.) do @if exist "%%a\.git" rd /s /q " ...

  3. c# 图文添加文字斜水印

    项目中有个添加水印的需求,需要给图片铺满斜水印. 网上搜了半天全是添加在图片上.下.左.右的案例. 于是按照网上的某一段案例自己修改了一些代码. Bitmap bitmap = new Bitmap( ...

  4. 用PHP抓取百度贴吧邮箱数据

    注:本程序可能非常适合那些做百度贴吧营销的朋友. 去逛百度贴吧的时候,经常会看到楼主分享一些资源,要求留下邮箱,楼主才给发. 对于一个热门的帖子,留下的邮箱数量是非常多的,楼主需要一个一个的去复制那些 ...

  5. ZigBee入门第一天

    按键查询控制灯的状态 1.宏定义灯和按键 2.按键和灯初始化 3.用if语句消抖的方法,实现按键控制灯的状态 相关寄存器 PxSEL PxDIR #include"ioCC2530.h&qu ...

  6. 《转载黑马教程》HTML&&CSS讲义,仅供参考

    今日内容: 1. HTML标签:表单标签 2. CSS: HTML标签:表单标签 * 表单: * 概念:用于采集用户输入的数据的.用于和服务器进行交互. * form:用于定义表单的.可以定义一个范围 ...

  7. SpringCloud解析之Zuul(一)

    本文基于Spring Cloud Edgware.SR6,Zuul版本1.3.1,解析Zuul的请求拦截机制,让大家对Zuul的原理有个大概的认识和了解.如有不对的地方,欢迎指正. spring bo ...

  8. Preface Numbering序言页码

    题面 (preface.pas/c/cpp) 一类书的序言是以罗马数字标页码的.传统罗马数字用单个字母表示特定的数值,以下是标准数字表: I 1 V 5 X 10 L 50 C 100 D 500 M ...

  9. UVA297 四分树 Quadtrees 题解

    题目链接: https://www.luogu.org/problemnew/show/UVA297 附几道推荐题目(先完成再食用此题效果更佳) https://www.luogu.org/probl ...

  10. Git的使用和配置小白必看都是干货,为您解惑

    Git安装 首先下载git这个软件,然后打开码云新建仓库 在本地选择一个路径作为本地仓库 点新建仓库然后输入邮箱和密码,然后进行配置 在要作为本地仓库的地方新建一个文件夹,保存后关闭,在文件夹空白处鼠 ...