后序遍历的优秀例题——851. 喧闹和富有

Posted C_YCBX Py_YYDS

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了后序遍历的优秀例题——851. 喧闹和富有相关的知识,希望对你有一定的参考价值。

题目


OJ平台

题目解析

这题实际上就是一个图的遍历,以下是输入示例对应的图形:

由于我们需要找到比某个编号有钱且安静值最小的,根据图形我们可以看出,在 0 结点之下的根节点都要比 0 有钱,我们只需要通过 dfs 遍历这颗树即可更新答案,但是会出现一个问题:如果使用的是前序的遍历则需要增加很多变量进行记录状态,且无法对这一次遍历走过的路径进行更新。

如何解决?

使用后序遍历即可,因为后序则相当于直接算出了所有子树的答案,然后再更新根节点,这样做正好符合本题的遍历思路。

解题代码

前序+记录

如果直接使用前序遍历进行答案更新,则需要每次遍历的时候把整个路径都搜索一遍,且需要一个变量贯穿始终来进行答案的更新!这里C++直接用左值引用即可。

为了防止太过暴力而超时,用check数组对每一次更新搜索过程进行状态记录,防止重复遍历。

解题代码:

class Solution 
public:
    vector<int> loudAndRich(vector<vector<int>>& richer, vector<int>& quiet) 
        int n = quiet.size();
        vector<int> record[n];
        for(int i=0;i<richer.size();i++)
            record[richer[i][1]].emplace_back(richer[i][0]);
        
        bool check[n];
        function<void(pair<int,int>&,int)> dfs = [&](pair<int,int>& ret,int next)
            for(auto t:record[next])
                if(ret.first>quiet[t])
                    ret.first = quiet[t];
                    ret.second = t;
                
                if(!check[t])
                    check[t] = 1;
                    dfs(ret,t);
                
            
        ;
        vector<int>ret(n);
        for(int i=0;i<n;i++)
            pair<int,int>reINT_MAX,i;
            memset(check,0,sizeof(check));
            dfs(re,i);
            ret[i] = quiet[i]<re.first?i:re.second;
        
        return ret;
    
;

后序遍历

由于根据题意,实际上后序遍历的顺序,正好符合题目的遍历先后依赖!直接后序即可。


解题代码:

class Solution 
public:
    vector<int> loudAndRich(vector<vector<int>> &richer, vector<int> &quiet) 
        int n = quiet.size();
        vector<vector<int>> g(n);
        for (auto &r : richer) 
            g[r[1]].emplace_back(r[0]);
        

        vector<int> ans(n, -1);
        function<void(int)> dfs = [&](int x) 
            if (ans[x] != -1) 
                return;
            
            ans[x] = x;
            for (int y : g[x]) 
                dfs(y);
                if (quiet[ans[y]] < quiet[ans[x]]) 
                    ans[x] = ans[y];
                
            
        ;
        for (int i = 0; i < n; ++i) 
            dfs(i);
        
        return ans;
    
;

以上是关于后序遍历的优秀例题——851. 喧闹和富有的主要内容,如果未能解决你的问题,请参考以下文章

851. 喧闹和富有

LeetCode 851 喧闹和富有[dfs] HERODING的LeetCode之路

LeetCode 807. 保持城市天际线 / 630. 课程表 III(贪心+优先队列)/ 851. 喧闹和富有(拓扑排序)

从喧闹与富有中搞懂搜索和拓扑

从喧闹与富有中搞懂搜索和拓扑

从喧闹与富有中搞懂搜索和拓扑