leetcode 210. 课程表 II medium
题目描述:
解题思路:
拓扑排序,用kahn算法
+ 算法流程
0. 设置邻接表,入度数组(nums[i] 表示 第i个节点的入度),结果数组Ret
1. 初始化队列,将入度为0的顶点全都入队(顺序不重要)
2. 出队队首元素,放入ret数组,同时把这个元素的所有邻接点入度减-1,假如入度为0,就入队。
3. 循环步骤2 直到队列为空
4. 如果ret数组长度与节点数目一致,ret数组就是其中一个拓扑排序,否则就是有环。
代码:
//
class Solution {
public:
vector<int> findOrder(int numCourses, vector<vector<int>>& prerequisites) {
vector<vector<int>> adjs(numCourses, vector<int>()); // 邻接表
vector<int> nums(numCourses, 0); // 入度数组
for(auto &edge: prerequisites){
adjs[edge[1]].push_back(edge[0]);
nums[edge[0]]++;
}
queue<int> q;
vector<int> ret;
for (int i = 0; i < numCourses; i++){
if (nums[i] == 0){
q.push(i);
}
}
while(q.size()){
int cur = q.front();
q.pop();
ret.push_back(cur);
for (int next: adjs[cur]){
nums[next]--;
if (nums[next] == 0){
q.push(next);
}
}
}
if (ret.size() == numCourses)
return ret;
else
return {};
}
};
leetcode 207. 课程表 medium
题目描述:
解题思路:
能找的到拓扑排序,就是有向无环图,否则就是有环
代码:
//
class Solution {
public:
bool canFinish(int numCourses, vector<vector<int>>& prerequisites) {
// 转为邻接表 和入度数组
vector<vector<int>> adjs(numCourses);
vector<int> nums(numCourses);
for (vector<int> &edge: prerequisites){
adjs[edge[1]].push_back(edge[0]);
nums[edge[0]]++;
}
queue<int> q;
for (int i = 0; i< numCourses; i++){
if (nums[i] == 0){
q.push(i);
}
}
vector<int> ret;
while (q.size()){
int cur = q.front();
ret.push_back(cur);
q.pop();
for (int next: adjs[cur]){
nums[next]--;
if (nums[next] == 0){
q.push(next);
}
}
}
return ret.size() == numCourses;
}
};