C++---树形DP---树的中心(每日一道算法2023.7.19)

news2024/10/3 22:24:52

注意事项:
本题为"树形DP—树的最长路径"的近似题,同时涉及到 单链表模拟邻接表存储图 的操作,建议先理解那篇文章。

题目:
给定一棵树,树中包含 n 个结点(编号1~n)和 n−1 条无向边,每条边都有一个权值。
请你在树中找到一个点,使得该点到树中其他结点的最远距离最近。

输入格式
第一行包含整数 n。
接下来 n−1 行,每行包含三个整数 ai,bi,ci,表示点 ai 和 bi 之间存在一条权值为 ci 的边。

输出格式
输出一个整数,表示所求点到树中其他结点的最远距离。

数据范围
1≤n≤10000,1≤ai,bi≤n,1≤ci≤105

输入:
5 
2 1 1 
3 2 1 
4 3 1 
5 1 1
输出:
2
#include <cmath>
#include <cstring>
#include <algorithm>
#include <iostream>
#include <queue>
using namespace std;

const int N = 10010, M = N*2, INF = 0x3f3f3f3f;   //无向边,M开点数的两倍
int n;
int h[N], e[M], ne[M], w[M], idx = 0;       //邻接表链表模拟
int d1[N], d2[N], p1[N], up[N];       //d1[i]为点i向下的最长路径的长度,d2[i]为次长路径的长度,p1[i]为点i的最长路径的下一个点是谁,u[i]为点i向上的最长路径的长度

//经典的邻接表-链表模拟 存储图/树
void add(int a, int b, int c) {
    e[idx] = b;
    w[idx] = c;
    ne[idx] = h[a];
    h[a] = idx++;
}

//向下找最长路径和次长路径,用子节点信息更新父节点,并返回最长路径的长度
int dfs_down(int u, int father) {
    //遍历所有点,找到从u点向下走的最长路径和次长路径
    for (int i = h[u]; i != -1; i = ne[i]) {
        int j = e[i];
        if (j == father) continue;               //向下找,所以不能向父节点找路

        int d = dfs_down(j, u) + w[i];    //求出从u点向j点走,再向其他点走的最长路径的长度

        //判断当前的这条路径是否能替换最长路径或者次长路径,并更新p1数组进行记录最长路径的下一个点
        if (d >= d1[u]) {
            d2[u] = d1[u], d1[u] = d;
            p1[u] = j;
        }
        else if (d > d2[u]) {
            d2[u] = d;
        }
    }
    return d1[u];
}

//还是向下遍历树,但这次是用当前点u来更新点j的状态,也就是父节点信息更新子节点
void dfs_up(int u, int father) {
    for (int i = h[u]; i != -1; i = ne[i]) {
        int j = e[i];
        if (j == father) continue;

        //如果点u的最长路径的下一个点(p1[u])是点j,那么就不能选最长路径来更新
        if (p1[u] == j) up[j] = max(up[u], d2[u]) + w[i];
        else up[j] = max(up[u], d1[u]) + w[i];

        dfs_up(j, u);
    }
}

int main() {
    //读入
    cin >> n;
    memset(h, -1, sizeof h);   //所有链表初始都指向-1
    for (int i = 0; i<n-1; i++) {
        int a, b, c;
        cin >> a >> b >> c;
        add(a, b, c), add(b, a, c);    //无向边,那就a->b,b->a双向边即可
    }

    dfs_down(1, -1);
    dfs_up(1, -1);

    //枚举所有点的向上和向下的情况,求出最短距离
    int res = INF;
    for (int i = 1; i<=n; i++) {
        res = min(res, max(d1[i], up[i]));
    }
    cout << res;
}

思路:
这个题和"树的最长路径"很相似,“树的最长路径”是只要求出 点向下的最长和次长路径的长度相加即可,
而这道题多了一种向上找路径的可能,那么不妨举个例子,还是和上题一样,将整个树“拎起来”,类似拓扑结构:
请添加图片描述
接下来以p1代表点一,p2代表点2
假设现在遍历到了p2,那如何求出p2到所有点的最长路径的长度?

条件1. 从当前节点往下,直到子树中某个叶节点的最长路径。
将p2能到的每条路(除了父节点p1)都dfs一遍即可。

条件2. 从当前节点往上走到其父节点,再从其父节点出发且不回到该节点的最长路径。
还是从上往下遍历,但这次是用p1来更新p2,首先判断p1的向下最长路径是否经过p2,
1.如果未经过p2,那么就可以直接更新p2的向上最长路径,也就是p1到p2的距离+p1的最长向下路径的长度,
2.如果经过p2,那么就说明p1的向下最长路径经过p2,也就不能使用最长路径了,这也就是为什么需要求出次长路径的原因,接着更新p2的向上最长路径,也就是p1到p2的距离+p1的次长向下路径的长度。

对所有的点进行上述两个条件的计算,再取max即为这个点到所有点的最长距离,
再将每个点的这个结果取min,即为树中某节点到其他所有节点最远距离最近的答案。

如果有所帮助请给个免费的赞吧~有人看才是支撑我写下去的动力!

声明:
算法思路来源为y总,详细请见https://www.acwing.com/
本文仅用作学习记录和交流

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

pandas清洗客户编码异常数据

前言 在不同行业中&#xff0c;我们经常会遇到一个麻烦的问题&#xff1a;数据清洗。尤其是当我们需要处理客户编码异常数据时&#xff0c;这个问题变得尤为重要。想象一下&#xff0c;许多银行都是以客户为单位管理数据的&#xff0c;因此每个客户都有一个独特的编码。在处理…

LiveGBS流媒体平台GB/T28181功能-海康NVR摄像机自带物联网卡摄像头注册GB/T28181国标平台看不到设备的时候如何抓包及排查

海康大华宇视华为等硬件NVR摄像机注册到LiveGBS国标平台看不到设备的时候如何抓包及排查 1、设备注册后查看不到1.1、是否是自带物联网卡的摄像头1.2、关闭萤石云1.3、防火墙排查1.4、端口排查1.5、IP地址排查1.6、设备TCP/IP配置排查1.7、设备多网卡排查1.8、设备接入配置参数…

实战:ELK环境部署并采集springboot项目日志

文章目录 前言技术积累ELK组成及功能框架搭建基础 EIK环境搭建elasticsearch配置相关kibana配置相关logstash配置相关elk目录下增加docker-compose文件查看elk目录文件树编排elk springboot集成logstashpom.xmllogback-spring.xml启动项目logstash采集日志 写在最后 前言 相信…

Java8 stream toMap、groupingBy、mapping的综合应用

文章目录 一、stream toMap、groupingBy、mapping的综合应用1、前提准备①、实体类②、数据准备 2、核心代码&#xff1a;3、运行结果 一、stream toMap、groupingBy、mapping的综合应用 1、前提准备 ①、实体类 package com.cfay.demo;import lombok.AllArgsConstructor; i…

LCD拼接屏、LED显示屏和OLED显示屏的主要区别

我们在生活或工作中经常看到大大小小的显示屏&#xff0c;但很多人却分不清楚这些屏到底属于哪一类&#xff0c;今天sostron与大家一起来分享下关于&#xff1a;LCD拼接屏、LED显示屏、OLED透明屏三者的区别。 LCD拼接屏、LED显示屏和OLED显示屏是不同类型的显示技术&#xff0…

【116个】网络安全测试相关面试真题

1、Burpsuite常用的功能是什么&#xff1f; 2、reverse_tcp和bind_tcp的区别&#xff1f; 3、拿到一个待检测的站或给你一个网站&#xff0c;你觉得应该先做什么&#xff1f; 4、你在渗透测试过程中是如何敏感信息收集的&#xff1f; 5、你平时去哪些网站进行学习、挖漏洞提交到…

这样创建客户帮助中心,效果超好!

创建一个有效的客户帮助中心是为了为客户提供优质的支持和服务。在这个数字化时代&#xff0c;客户期望能够快速找到所需的信息&#xff0c;并得到准确和及时的解答。本文将分享创建有效客户帮助中心的最佳实践&#xff0c;帮助您提供出色的客户体验并提升客户满意度。 1. 了解…

Banana Pi M2 Zero 运行 openHAB 回顾

首先我要透露的是&#xff0c;BPI 的工作人员向我发送了一台免费的 BPi M2 Zero 来执行这些测试。我相信我的评论是公平和公正的&#xff0c;但我想坦率地说明这一事实。 硬件简介 与 Raspberry Pi Zero W 相比&#xff0c;Banana Pi BPI-M2 Zero 具有令人印象深刻的规格。以下…

git进阶操作

一、git 基础概念1. 1.1 三种状态&#xff1a; 工作区&#xff08;unstage&#xff09;——已修改&#xff08;modified&#xff09; 暂存区&#xff08;stage&#xff09;——已暂存&#xff08;staged&#xff09; 对象区——已提交&#xff08;commited&#xff09; 工作…

moment.js常见格式化处理各种时间方法

Moment.js 是一个简单易用的轻量级 JavaScript 日期处理类库,提供了日期格式化、日期解析等功能。它支持在浏览器和 NodeJS 两种环境中运行。此类库能够将给定的任意日期转换成多种不同的格式,具有强大的日期计算功能,同时也内置了能显示多样的日期形式的函数。另外,它也支…

博弈论--sg函数

sg函数------ 定义终止状态的SG函数值为0。如果游戏已经结束&#xff0c;即达到了终止状态&#xff0c;那么对应的SG函数值就是0。即先手的sg值为0&#xff0c;则先手必败&#xff0c;否则先手必胜。 如何求sg函数值--------对于每个可能的移动&#xff0c;将后续状态的SG函数…

「从零入门推荐系统」21:chatGPT、大模型介绍

作者 | gongyouliu 编辑 | gongyouliu 自2022年11月30日OpenAI发布chatGPT以来&#xff0c;大模型技术掀起了新一轮人工智能浪潮。chatGPT在各个领域&#xff08;包括对话、摘要、内容生成、问题解答、识图、数学计算与推理、代码编写等&#xff09;取得了比之前算法好得多的成…

测试开发之路 (工具篇)--Docker

目录 前言 什么是 docker 在 demo 中学习 mysql test link 更复杂点的场景 前言 Docker是一种开源的容器化平台&#xff0c;它可以帮助开发人员和测试人员更轻松地构建、部署和运行应用程序。在测试开发中&#xff0c;Docker可以提供许多便利和优势。 什么是 docker 官…

VMware Cloud Director 10.5 - 领先的云服务交付平台

VMware Cloud Director 10.5 - 领先的云服务交付平台 Support for vSphere 8.0U1 & NSX 4.1 请访问原文链接&#xff1a;https://sysin.org/blog/vmware-cloud-director-10/&#xff0c;查看最新版。原创作品&#xff0c;转载请保留出处。 作者主页&#xff1a;sysin.or…

【ShenYu系列】ShenYu的SPI实现源码分析

前言 前面我已经介绍【面试系列】详细拆解Java、Spring、Dubbo三者SPI机制的原理&#xff0c;当已经有了合适的实现&#xff0c;shenyu自身的SPI和上面的有啥区别&#xff0c;值得玩味。 什么是SPI SPI就是Service Provider Interface&#xff0c;直译"服务提供方接口&…

go+vue+wails写一个简单的密码加密器

git仓库 gitee: malred/password-generator-wails-vue gitee&#xff1a; malred/password-generator-wails-vue github: https://github.com/malred/password-generator-wails-vue wails是什么 我们用它来套壳前端项目&#xff08;vue&#xff09;&#xff0c;打包成桌面端…

Java虚拟机——类加载机制概述 类加载的时机

在Class文件中描述的各类信息&#xff0c;最终都需要加载到虚拟机中之后才能被运行和使用。本章将会介绍虚拟机如何加载这些Class文件&#xff0c;Class文件中的信息进入到虚拟机后会发生什么变化。类加载机制&#xff1a;Java虚拟机把描述类的数据从Class文件加载到内存&#…

【ArcGIS】shp导入报错ORA-00911无效字符

这个当个问题记录以下&#xff0c;就是shp文件名或者字段名有非正常字符&#xff0c;修改下名称重新导入即可&#xff1b; 直接改shp没法修改字段&#xff0c;会报错&#xff0c;需要先转化为gdb文件&#xff0c;然后在修改

【Spring】Spring AOP入门及实现原理剖析

文章目录 1 初探Aop1.1 何为AOP&#xff1f;1.2 AOP的组成1.2.1 切面(Aspect)1.2.2 连接点(Join Point)1.2.3 切点(Pointcut)1.2.4 通知(Advice) 1.3 AOP的使用场景 2 Spring AOP入门2.1 添加 Spring AOP 框架⽀持2.2 定义切面和切点2.3 定义相关通知 3 Spring AOP实现原理3.1 …

tauri自定义窗口window并实现拖拽和阴影效果

需求说明 由于官方提供的窗口标题并不能实现我的需求&#xff0c;不能很好的实现主题切换的功能&#xff0c;所以根据官方文档实现了一个自定义的窗口&#xff0c;官方文档地址&#xff1a;Window Customization | Tauri Apps 但是实现之后&#xff0c; 没有了窗体拖拽移动的…