每日一题802. 找到最终的安全状态

Posted 7TribeZ

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了每日一题802. 找到最终的安全状态相关的知识,希望对你有一定的参考价值。

802. 找到最终的安全状态

难度中等241

在有向图中,以某个节点为起始节点,从该点出发,每一步沿着图中的一条有向边行走。如果到达的节点是终点(即它没有连出的有向边),则停止。

对于一个起始节点,如果从该节点出发,无论每一步选择沿哪条有向边行走,最后必然在有限步内到达终点,则将该起始节点称作是 安全 的。

返回一个由图中所有安全的起始节点组成的数组作为答案。答案数组中的元素应当按 升序 排列。

该有向图有 n 个节点,按 0 到 n - 1 编号,其中 n 是 graph 的节点数。图以下述形式给出:graph[i] 是编号 j 节点的一个列表,满足 (i, j) 是图的一条有向边。

示例 1:

输入:graph = [[1,2],[2,3],[5],[0],[5],[],[]]
输出:[2,4,5,6]
解释:示意图如上。

示例 2:

输入:graph = [[1,2,3,4],[1,2],[3,4],[0,4],[]]
输出:[4]

提示:

  • n == graph.length
  • 1 <= n <= 104
  • 0 <= graph[i].length <= n
  • graph[i] 按严格递增顺序排列。
  • 图中可能包含自环。
  • 图中边的数目在范围 [1, 4 * 104] 内。

 

方法一:深度优先搜索 + 三色标记法


根据题意,若起始节点位于一个环内,或者能到达一个环,则该节点不是安全的。否则,该节点是安全的。

我们可以使用深度优先搜索来找环,并在深度优先搜索时,用三种颜色对节点进行标记,标记的规则如下:

白色(用 00 表示):该节点尚未被访问;
灰色(用 11 表示):该节点位于递归栈中,或者在某个环上;
黑色(用 22 表示):该节点搜索完毕,是一个安全节点。
当我们首次访问一个节点时,将其标记为灰色,并继续搜索与其相连的节点。

如果在搜索过程中遇到了一个灰色节点,则说明找到了一个环,此时退出搜索,栈中的节点仍保持为灰色,这一做法可以将「找到了环」这一信息传递到栈中的所有节点上。

如果搜索过程中没有遇到灰色节点,则说明没有遇到环,那么递归返回前,我们将其标记由灰色改为黑色,即表示它是一个安全的节点。

class Solution {
public:
    vector<int> eventualSafeNodes(vector<vector<int>> &graph) {
        int n = graph.size();
        vector<int> color(n);

        function<bool(int)> safe = [&](int x) {
            if (color[x] > 0) {
                return color[x] == 2;
            }
            color[x] = 1;
            for (int y : graph[x]) {
                if (!safe(y)) {
                    return false;
                }
            }
            color[x] = 2;
            return true;
        };

        vector<int> ans;
        for (int i = 0; i < n; ++i) {
            if (safe(i)) {
                ans.push_back(i);
            }
        }
        return ans;
    }
};

以上是关于每日一题802. 找到最终的安全状态的主要内容,如果未能解决你的问题,请参考以下文章

LeetCode802. 找到最终的安全状态(图论三色标记法拓扑排序)/847. 访问所有节点的最短路径(特殊的bfs,状态压缩,dp)

Leetcode 802 找到最终的安全状态(拓扑)

[LeetCode] 802. Find Eventual Safe States 找到最终的安全状态

leetcode 802. 找到最终的安全状态(Find Eventual Safe States)

LeetCode 802 找到最终的安全状态[DFS 三色标记法] HERODING的LeetCode之路

爱创课堂每日一题第十一天常见web安全及防护原理