zoukankan      html  css  js  c++  java
  • leetcode207

    拓扑排序问题。

    class Solution {
    public:
        bool canFinish(int numCourses, vector<pair<int, int>>& prerequisites) {
            int Hash[10010];//每个节点的入度
            vector<vector<int>> v(numCourses);//用于存储每个节点相邻的边
            stack<int> s;//存放入度为0的节点
        memset(Hash, 0, sizeof(Hash));
        for(int i =0 ; i < prerequisites.size();i++){
            pair<int, int>p = prerequisites[i];
            int x = p.first;
            int y = p.second;
            cout<<"x = "<<x <<"y = "<<y<<endl;
            v[x].push_back(y);
            ++Hash[y];
        }
        for(int i = 0; i < numCourses; i++){
            if(Hash[i] == 0){
                s.push(i);
            }
        }
        while (!s.empty()) {
            int cur = s.top();//找到入度为0的点
            s.pop();
            for(int i = 0; i < prerequisites.size(); i++){
                pair<int, int>p = prerequisites[i];
                int x = p.first;
                int y = p.second;
                if(cur == x){
                    for(int j = 0; j < v[cur].size(); j++){
                        --Hash[v[cur][j]];//删除以该点为起点的所有有向边
                        if(Hash[v[cur][j]] == 0)
                            s.push(v[cur][j]);
                    }
                    break;
                }
            }
        }
        for(int i = 0; i < numCourses; i++){
            if(Hash[i] != 0)
                return false;
        }
        return true;
        }
    };

    补充一个python的实现:

     1 class Solution:
     2     #返回True表示有环,返回False表示无环
     3     def dfs(self,visited,memo,dic,i):
     4         if visited[i]:
     5             return True
     6         if memo[i] == 0:
     7             return False
     8         elif memo[i] == 1:
     9             return True
    10         for cs in dic[i]:
    11             visited[i] = True
    12             bl = self.dfs(visited,memo,dic,cs)
    13             visited[i] = False
    14             if bl:
    15                 #当前线路中出现了环,则标记当前课程为1,返回True
    16                 memo[i] = 1
    17                 return True
    18         ##当前线路,已经找到最早的前置课程,没有出现"",则标记为0,表示课程i是可以学习的
    19         memo[i] = 0
    20         return False#返回False表示无环,当前课程i,可以完成学习
    21 
    22     def canFinish(self, numCourses: 'int', prerequisites: 'List[List[int]]') -> 'bool':
    23         dic = {}
    24         n = len(prerequisites)
    25         for i in range(numCourses):
    26             dic[i] = []
    27         for i in range(n):
    28             cs = prerequisites[i][0]#当前课程
    29             pre = prerequisites[i][1]#前置课程
    30             dic[cs].append(pre)
    31         visited = [False for _ in range(numCourses)]
    32         memo = [-1 for _ in range(numCourses)]
    33         for i in range(numCourses):
    34             #只要出现过一个有环的线路,则不能符合题目"所有课程都完成"的目标
    35             if self.dfs(visited,memo,dic,i):
    36                 return False
    37         return True

    算法思路:深度优先遍历,判断图中是否有环。

    使用两个标记数组:

    visited=True表示当前“线路”上的节点已经被锁定,如果在线路遍历的过程中遇到已经被锁定的节点,那说明遇到了环。

    memo表示备忘录(缓存),默认状态为-1,标记为0表示本节点不存在环,标记为1表示本节点有环,使用备忘录可加速得到查询结果。

  • 相关阅读:
    Javascript中eval解析的json的几种用法
    使用JSONlib简单的转换json操作
    Oracle12c导入scott测试用户(转)
    javascript中隐藏显示的样式表属性
    利用递归级联删除的代码
    递归(c++)(转)
    学习web开发遇到几个细节问题
    AJAX代码格式
    AJAX简介(转)
    算法训练 调和数列问题
  • 原文地址:https://www.cnblogs.com/asenyang/p/9746691.html
Copyright © 2011-2022 走看看