968.监控二叉树 树上最小支配集

 法一: 动态规划

一个被支配的节点只会有三种状态

        1.它本身有摄像头

        2.他没有摄像头, 但是它的父节点有摄像头

        3.他没有摄像头, 但是它的子节点有摄像头

我们 dfs(node,state) 记录在node节点时(以node为根的子树),状态为state下的所有最小摄像头

// 本身有摄像头就看左右孩子了

dfs(node,1) = min(dfs(node->left,1),dfs(node->left,2),dfs(node->left,3)) +

                      min(dfs(node->right,1),dfs(node->right,2),dfs(node->right,3)) + 1

// 本身没有摄像头, 左右孩子不能是2

dfs(node,2) = min(dfs(node->left,1),dfs(node->left,3)) +

                      min(dfs(node->left,1),dfs(node->left,3))

// 本身没有摄像头, 要靠子节点保障,同样左右孩子不能是2,而且至少有一个1

dfs(node,3) = min(dfs(node->left,1)+dfs(root->right,3), dfs(node->left,3)+dfs(node->right,1), 

                       dfs(node->left,1)+dfs(root->right,1))

边界条件怎么思考呢:

        tmp=dfs(nullptr,state)  state为1,tmp是INT_MAX/2  state为2,3,tmp是0

        因为state不应该是1,也就是叶子节点的不应该是用nullptr保障 ,所以我们把这种情况要筛掉

        而当他是2,3时,也就是说让nullptr的监控让他的父节点或者子节点保障,但是因为nullptr不需要监控,所以返回0就行

 代码如下:

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode() : val(0), left(nullptr), right(nullptr) {}
 *     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
 *     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}
 * };
 */
class Solution {
public:
    //最小支配集 
    int minCameraCover(TreeNode* root) {
        // 首先对于 一个节点,要被覆盖只有三种情况 
        //1. 它本身安装了摄像头                  ->记成蓝色 blue 0
        //2.(他没安装)它的父节点安装了摄像头      ->记成红色 red 1
        //3.(他没安装)它的孩子有一个安装了摄像头  ->记成黄色 yellow 2

        //对于根节点是蓝色 ans = min(l_blue,l_red,l_yellow) + min(r_blue,r_red,r_yellow) + 1
        //对于根节点是红色,子节点不能是红色 ans = min(l_blue,l_yellow) + min(r_blue,r_yellow)
        //对于根节点是黄色,子节点不能是红色 ans = min(l_blue+r_yellow, l_yellow+r_blue, l_blue+r_blue)
        map<pair<TreeNode*,int>,int> memo;
        function<int(TreeNode*,int)> dfs=[&](TreeNode* root,int color)->int{
            if(!root){
                if(color==0) return INT_MAX/2;  //
                else return 0; 
            }
            if(memo.count({root,color})) return memo[{root,color}];
            //null节点不能是蓝色 因为叶子节点不能把希望寄托在null上 把这种情况排除
            //但是null节点可以是红色或者黄色 
            //红色意味着该null也被监视了,虽然没必要,但是也不算错
            //黄色意味着该节点的安全由子节点保证 但是本来这个节点就是null 不用保证其安全
            if(color==0){
                return memo[{root,color}]=min(dfs(root->left,0),min(dfs(root->left,1),dfs(root->left,2))) + min(dfs(root->right,0),min(dfs(root->right,1),dfs(root->right,2))) + 1;
            }else if(color==1){
                return memo[{root,color}]=min(dfs(root->left,0),dfs(root->left,2)) + min(dfs(root->right,0),dfs(root->right,2));
            }else {
                return memo[{root,color}]=min(dfs(root->left,0)+dfs(root->right,2),min(dfs(root->left,2)+dfs(root->right,0),dfs(root->left,0)+dfs(root->right,0)));
            }
        };
        return min(dfs(root,0),dfs(root,2));
    }
};

法二: 贪心

        我们跳出思维定式来看看这个题,怎么 "贪心地" 使得使用最少的节点来支配整个树,显然在一层一层的来看,叶子节点不要放,在叶子节点的父节点放摄像头,然后跳过两个,在这一层放摄像头,然后再跳过两个,在这一层放摄像头,一直这样到根节点. 

        算法的正确可以这样想,叶子节点a一定要被监控,显然放在a的双亲是收益最大的,然后往上找没有监控的节点,用同样的贪心思想

        至于为什么不从根节点往下呢,可以这样想: 叶子节点一定是比根节点要多的,所以应该抓大头

我们把所有节点分成三种情况:

        0. 本身放了摄像头

        1. 本身没有摄像头,但是被子节点监控了

        2. 本身没有摄像头,但是被父节点监控了

这样就是说nullptr往上返回1, (因为显然不会是0,而为了让摄像头最少,又不能是2)

上一层如果收到了下面的两个1,就返回一个2

上一层如果收到了下面的2,就往上返回0 (只要收到一个2)

上一层如果收到了下面的0,就往上返回1 (只要收到一个0)

如果收到了一个0,一个2呢, 显然返回是0, 不如就会有一个节点没有被监控

而最后走到根节点又没有父节点,所有如果根节点返回2, ans是要加1的

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode() : val(0), left(nullptr), right(nullptr) {}
 *     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
 *     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}
 * };
 */
class Solution {
public:
    //最小支配集 
    int minCameraCover(TreeNode* root) { 
        int res=0;
        function<int(TreeNode*)> travel=[&](TreeNode*root)->int{
            if(!root) return 1;
            int left=travel(root->left);
            int right=travel(root->right);
            if(left==1 && right==1) return 2;               //情况1 
            if(left==2 || right==2) { res++; return 0;}     //情况2
            if(left==0 || right==0) return 1;               //情况3  

            return -1;
        };
        if(travel(root)==2) res++;
        return res;
    }
};

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/580964.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

投影连接Samba服务

目录 0.创建【Samba服务】 1.下载・安装一个能连接【Samba服务】的播放器 2.配置语言 3.配置服务器连接 0.创建【Samba服务】 Linux&#xff08;Ubuntu&#xff09;中创建【samba】服务&#xff0c;用于和Windows系统之间共享文件_ubuntu samba-CSDN博客 1.下载・安装一…

《深入理解mybatis原理》 MyBatis的架构设计以及实例分析

《深入理解mybatis原理》 MyBatis的架构设计以及实例分析 MyBatis是目前非常流行的ORM框架&#xff0c;它的功能很强大&#xff0c;然而其实现却比较简单、优雅。本文主要讲述MyBatis的架构设计思路&#xff0c;并且讨论MyBatis的几个核心部件&#xff0c;然后结合一个select查…

Matlab进阶绘图第51期—带填充等高线的三维特征渲染散点图

带填充等高线的三维特征渲染散点图是填充等高线图与特征渲染三维散点图的组合。 其中&#xff0c;填充等高线图与特征渲染的三维散点图的颜色用于表示同一个特征。 由于填充等高线图无遮挡但不直观&#xff0c;特征渲染的三维散点图直观但有遮挡&#xff0c;而将二者组合&…

【C++杂货铺】二叉搜索树

目录 &#x1f308;前言&#x1f308; &#x1f4c1; 二叉搜索树的概念 &#x1f4c1; 二叉搜索树的操作 &#x1f4c2; 二叉搜索树的查找 &#x1f4c2; 二叉搜索树的插入 &#x1f4c2; 二叉搜书树的删除 &#x1f4c1; 二叉搜索树的应用 &#x1f4c1; 二叉搜索树的…

vue3 h5模板

vue3的h5模板 基于vue3tsvantrem的h5模板 觉得帮到你了就给个start

【win10移动热点,提示正在获取ip地址...】

检查 Wired AutoConfig/ WLAN AutoConfig 服务运行 电脑→管理→服务和应用程序→服务&#xff1a;AutoConfig 有线网络无线网卡 1.开启wifi热点&#xff0c;自动生成“本地连接*10”&#xff1b; 2.配置Wired LAN网络共享 仅无线网卡 1. 开启wifi热点&#xff0c;自动生…

自学Python爬虫js逆向(二)chrome浏览器开发者工具的使用

js逆向中很多工作需要使用浏览器中的开发者工具&#xff0c;所以这里以chrome为例&#xff0c;先把开发者工具的使用总结一下&#xff0c;后面用到的时候可以回来查询。 Google Chrome浏览器的开发者工具是前端开发者的利器&#xff0c;它不仅提供了丰富的功能用于开发、调试和…

电动公共交通车充电站设置储能电站方案

相比于传统燃油公交车&#xff0c;电动公交车以电代油&#xff0c;具有零排放、低噪音、低能耗等优势。随着电池、车载电机等相关技术的不断发展&#xff0c;电动公交车在国内乃至全世界范围内逐步推广应用。动力电池是电动公交车的重要部件之一&#xff0c;其寿命及性能影响着…

解密推理部署工程师的必备技能,面试题库分析

推理部署工程师面试题库 1. 描述一下SM的结构&#xff1f; 英伟达 GPU 架构&#xff1a;* 计算核心&#xff1a;INT32、FP32、FP64 CUDA 核心&#xff0c;Tensor 核心&#xff0c;超低延迟负载/存储。* 调度和存储器&#xff1a;Warp 调度器注册文件&#xff0c;共享存储器&am…

逻辑回归模型与GBDT+LR——特征工程模型化的开端

随着信息技术和互联网的发展&#xff0c; 我们已经步入了一个信息过载的时代&#xff0c;这个时代&#xff0c;无论是信息消费者还是信息生产者都遇到了很大的挑战&#xff1a; 信息消费者&#xff1a;如何从大量的信息中找到自己感兴趣的信息&#xff1f;信息生产者&#xff…

主题乐园私域精细化运营

主题乐园私域精细化运营是指在细分用户群体的基础上&#xff0c;通过个性化、精准的运营方式&#xff0c;为用户提供定制化服务和体验。以下是一些常见的主题乐园私域精细化运营玩法&#xff1a; 会员制度和会员专属服务&#xff1a;建立完善的会员制度&#xff0c;为会员提供专…

碳实践 | 一文读懂LCA产品生命周期环境影响评价

一、产品生命周期评价定义 生命周期评价&#xff1a;生命周期评价&#xff08;Life Cycle Assessment&#xff0c;简称LCA&#xff09;是一种量化评价方法。它涵盖了产品的整个生命周期——从自然资源开采到原材料加工、产品制造、分销、使用&#xff0c;直至最终废弃处置或回…

mongodb使用debezium

前置 服务器上需要安装jdk11 jdk下载地址 kafka安装 官网下载地址 安装教程 debezium 安装 运行 Debezium 连接器需要 Java 11 或更高版本 Debezium 并不是一个独立的软件&#xff0c;而是很多个 Kafka 连接器的总称。这些 Kafka 连接器分别对应不同的数据库&#xff0c;…

使用Cesium ion将 Sketchfab 3D 模型添加到您的GIS应用中

您现在可以将 Sketchfab 中的 3D 模型导入 Cesium ion 中以创建 3D 块&#xff0c;从而更轻松地为地理空间体验创建上下文和内容。 Sketchfab 是 Epic Games 的一部分&#xff0c;也是使用最广泛的 3D 资产市场之一。自 2012 年推出以来&#xff0c;已有超过 1000 万用户使用 …

2024/4/28 C++day5

有以下类&#xff0c;完成特殊成员函数 class Person { string name; int *age; } class Stu:public Person { const double score; } #include <iostream> #include <string> using namespace std; class Person { string name; int *age ; publi…

Kafka报错ERROR Exiting Kafka due to fatal exception during startup

报错&#xff1a; ERROR Exiting Kafka due to fatal exception during startup. (kafka.Kafka$) kafka.common.InconsistentClusterIdException: The Cluster ID FSzSO50oTLCRhRnRylihcg doesnt match stored clusterId Some(0oSLohwtQZWbIi73YUMs8g) in meta.properties. Th…

手撕红黑树(kv模型模拟)

目录 前言 一、相关概念 二、性质介绍 红黑树平衡说明 三、红黑树模拟&#xff08;kv结构&#xff09; 1、红黑树节点 2、红黑树插入 2、特殊处理情况 声明&#xff1a; 情况一&#xff1a;cur为红&#xff0c;p为红&#xff0c;g为黑&#xff0c;u存在&#xff0c;且…

MyBatis 核心配置讲解(下)

大家好&#xff0c;我是王有志&#xff0c;一个分享硬核 Java 技术的互金摸鱼侠。 我们书接上回&#xff0c;继续聊 MyBatis 的核心配置&#xff0c;我们今天分享剩下的 5 项核心配置。 不过正式开始前&#xff0c;我会先纠正上一篇文章 MyBatis 核心配置讲解&#xff08;上&…

QAnything知识库问答系统离线部署(LLM+RAG)

一、QAnything介绍 &#xff08;一&#xff09;简介 QAnything 是网易有道开源的一个问答系统框架&#xff0c;支持私有化部署和SaaS服务两种调用形式。它能够支持多种格式的文件或数据库&#xff0c;提供准确、快速和可靠的问答体验。目前已支持的文件格式包括PDF、Word、PP…

防火墙对要保护的服务器做端口映射的好处是几个

防火墙对要保护的服务器进行端口映射具有多重好处&#xff0c;这些好处主要围绕网络安全性、灵活性和可管理性展开。以下是对这些好处的专业分析&#xff1a; 1. 增强网络安全性&#xff1a;端口映射允许防火墙对进入服务器的流量进行精确控制。通过映射特定端口&#xff0c;防…