LeetCode-210 Course Schedule II

题目描述

There are a total of n courses you have to take, labeled from 0 to n-1.

Some courses may have prerequisites, for example to take course 0 you have to first take course 1, which is expressed as a pair: [0,1]

Given the total number of courses and a list of prerequisite pairs, return the ordering of courses you should take to finish all courses.

There may be multiple correct orders, you just need to return one of them. If it is impossible to finish all courses, return an empty array.

 

题目大意

题意同LeetCode-207 Course Schedule,但需要返回看书的顺序(如果存在多个解,则返回其中之一)。

 

示例

E1

Input: 2, [[1,0]] 
Output: [0,1]

E2

Input: 4, [[1,0],[2,0],[3,1],[3,2]]
Output: [0,1,2,3] or [0,2,1,3]

 

解题思路

依然使用DFS来遍历所有可能性,但需要保存可能的返回结果,算法中需要使用两个数组来分别保存图节点的访问情况,其中第一个数组表示本次以K为源节点进行DFS遍历时所访问的节点,第二个数组表示在所有的访问情况中结点的访问状态。(PS:语言表达看似很复杂,实际看到代码就应该很容易理解)

 

复杂度分析

时间复杂度:O(|V| + |E|)

空间复杂度:O(|V| + |E|)

 

代码

class Solution {
public:
    vector<int> findOrder(int numCourses, vector<vector<int>>& prerequisites) {
        vector<unordered_set<int> > edge(numCourses);
        vector<int> res;
        //对图的边进行二维数组保存
        for(int i = 0; i < prerequisites.size(); ++i) {
            edge[prerequisites[i][0]].insert(prerequisites[i][1]);
        }
        //表示以当前访问的结点为源点进行dfs时其余结点的访问情况
        vector<bool> todo(numCourses, false);
        //表示在所有结点访问的过程中的结点被访问情况
        vector<bool> done(numCourses, false);
        for(int i = 0; i < numCourses; ++i) {
            if(!done[i] && !dfs(res, edge, todo, done, i)) {
                return {};
            }
        }
        return res;
    }
    
    bool dfs(vector<int>& res, vector<unordered_set<int> >& edge, vector<bool>& todo, vector<bool>& done, int k) {
        //若该节点在本次DFS过程中以被访问,并且本次还要访问,则代表产生环
        if(todo[k])
            return false;
        //若该结点已被完全访问,其子节点也完全被遍历过,则表示该结点为终结点
        if(done[k])
            return true;
        todo[k] = done[k] = true;
        //DFS遍历结点K的子节点
        for(unordered_set<int>::iterator iter = edge[k].begin(); iter != edge[k].end(); ++iter) {
            if(!dfs(res, edge, todo, done, *iter))
                return false;
        }
        //若满足以上条件,则代表在这个小的以K为源点的遍历过程中,无环产生
        res.push_back(k);
        //为了不影响其他DFS过程中结点的访问情况,将该位置的访问情况进行还原
        todo[k] = false;
        return true;
    }
};

 

转载于:https://www.cnblogs.com/heyn1/p/11048172.html

LeetCode-Editor是一种在线编码工具,它提供了一个用户友好的界面编写和运行代码。在使用LeetCode-Editor时,有时候会出现乱码的问题。 乱码的原因可能是由于编码格式不兼容或者编码错误导致的。在这种情况下,我们可以尝试以下几种解决方法: 1. 检查文件编码格式:首先,我们可以检查所编辑的文件的编码格式。通常来说,常用的编码格式有UTF-8和ASCII等。我们可以将编码格式更改为正确的格式。在LeetCode-Editor中,可以通过界面设置或编辑器设置来更改编码格式。 2. 使用正确的字符集:如果乱码是由于使用了不同的字符集导致的,我们可以尝试更改使用正确的字符集。常见的字符集如Unicode或者UTF-8等。在LeetCode-Editor中,可以在编辑器中选择正确的字符集。 3. 使用合适的编辑器:有时候,乱码问题可能与LeetCode-Editor自身相关。我们可以尝试使用其他编码工具,如Text Editor、Sublime Text或者IDE,看是否能够解决乱码问题。 4. 查找特殊字符:如果乱码问题只出现在某些特殊字符上,我们可以尝试找到并替换这些字符。通过仔细检查代码,我们可以找到导致乱码的特定字符,并进行修正或替换。 总之,解决LeetCode-Editor乱码问题的方法有很多。根据具体情况,我们可以尝试更改文件编码格式、使用正确的字符集、更换编辑器或者查找并替换特殊字符等方法来解决这个问题。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值