【洛谷 P1364】医院设置 题解(图论+深度优先搜索)

2023-09-14 16:05:14

医院设置

题目描述

设有一棵二叉树,如图:

其中,圈中的数字表示结点中居民的人口。圈边上数字表示结点编号,现在要求在某个结点上建立一个医院,使所有居民所走的路程之和为最小,同时约定,相邻接点之间的距离为 1 1 1。如上图中,若医院建在 1 1 1 处,则距离和 = 4 + 12 + 2 × 20 + 2 × 40 = 136 =4+12+2\times20+2\times40=136 =4+12+2×20+2×40=136;若医院建在 3 3 3 处,则距离和 = 4 × 2 + 13 + 20 + 40 = 81 =4\times2+13+20+40=81 =4×2+13+20+40=81

输入格式

第一行一个整数 n n n,表示树的结点数。

接下来的 n n n 行每行描述了一个结点的状况,包含三个整数 w , u , v w, u, v w,u,v,其中 w w w 为居民人口数, u u u 为左链接(为 0 0 0 表示无链接), v v v 为右链接(为 0 0 0 表示无链接)。

输出格式

一个整数,表示最小距离和。

样例 #1

样例输入 #1

5						
13 2 3
4 0 0
12 4 5
20 0 0
40 0 0

样例输出 #1

81

提示

数据规模与约定

对于 100 % 100\% 100% 的数据,保证 1 ≤ n ≤ 100 1 \leq n \leq 100 1n100 0 ≤ u , v ≤ n 0 \leq u, v \leq n 0u,vn 1 ≤ w ≤ 1 0 5 1 \leq w \leq 10^5 1w105


思路

将二叉树储存为一张图,存图时要存双向边。

暴力枚举每个节点作为医院,然后分别计算所有节点到这个医院的距离的加权和。

使用 DFS 遍历整张图,对于当前遍历的节点 x x x,用一个变量 s u m sum sum 记录所有已经遍历的节点到当前节点 x x x 的距离的加权和,用一个 bitset 变量 v i s vis vis 记录所有已经遍历过的节点,然后递归地遍历 x x x 的所有邻接节点,计算它们到 x x x 的距离的加权和,并将其加到 s u m sum sum 上。

为了避免重复遍历已经遍历过的节点,并方便计算节点到达医院的距离,需要在遍历之前将 v i s [ x ] vis[x] vis[x] 设为 1 1 1,在遍历之后再将其设为 0 0 0

遍历完所有的节点后,用一个变量 a n s ans ans 记录所有节点作为医院时的最小距离和,然后每次更新 a n s = min ⁡ ( a n s , s u m ) ans=\min(ans,sum) ans=min(ans,sum)。最后输出 a n s ans ans 即可。


AC代码

#include <iostream>
#include <bitset>
#include <algorithm>
#include <cstring>
#define AUTHOR "HEX9CF"
using namespace std;

const int N = 1005;

// 链式前向星
struct Sedge
{
    int to;
    int next;
} edge[N];
int head[N];
int cnt = 0;
int w[N];

int n;
int tmp;
int sum;
int ans;

bitset<N> vis;

void add(int u, int v)
{
    if (u && v)
    {
        edge[cnt].to = v;
        edge[cnt].next = head[u];
        head[u] = cnt++;
    }
}

void dfs(int x)
{
    if (vis[x])
    {
        return;
    }
    sum += w[x] * vis.count();
    // cout << x << endl;
    vis[x] = 1;
    for (int i = head[x]; ~i; i = edge[i].next)
    {
        dfs(edge[i].to);
    }
    vis[x] = 0;
}

int main()
{
    memset(head, -1, sizeof(head));
    cin >> n;
    for (int i = 1; i <= n; i++)
    {
        int a, b;
        cin >> w[i] >> a >> b;
        add(i, a);
        add(i, b);
        add(a, i);
        add(b, i);
    }
    for (int i = 1; i <= n; i++)
    {
        sum = 0;
        vis.reset();
        dfs(i);
        if (1 == i)
        {
            ans = sum;
        }
        else
        {
            ans = min(ans, sum);
        }
        // cout << sum << endl;
    }
    cout << ans << endl;
    return 0;
}

更多推荐

springboot和vue:二、springboot特点介绍+热部署热更新

springboot特点介绍能够使用内嵌的Tomcat、Jetty服务器,不需要部署war文件。提供定制化的启动器Starters,简化Maven配置,开箱即用。纯Java配置,没有代码生成,也不需要XML配置。提供了生产级的服务监控方案,如安全监控、应用监控、健康检测等。热部署热更新SpringBoot提供了spri

SSD上 NVIDIA Jetson Orin NANO系統如何刷

对于AI计算性能高达40TOPS的JetsonOrinNano开发套件来说,如果缺少性能够好的存储相匹配,会让总体执行效益大打折扣。为此,NVIDIA在JetsonOrinNano开发套件上配置2个M.2接口(如下图),最高能安装2片高速PCIe总线的NVMe高速存储设备,这样大大提升了这个产品的实用性。由于M.2设备

Java中常见的线程池

一、Java中常见的线程池1.为什么使用线程池重用线程池的线程,避免因为线程的创造和销毁所带来的性能开销。有效控制线程池的最大并发数,避免大量的线程之间因抢占系统资源而阻塞。能够对线程进行简单的管理,并提供一些特定的操作,如:定时、定期、单线程、并发数控制等功能。2.线程池可能带来的风险死锁任何多线程应用程序都有死锁风

stm32单片机之外部脉冲捕获例程

stm32单片机之外部脉冲捕获例程定时器通道1来捕获外部脉冲,并且当脉冲到来时,通过HAL库的回调函数来处理这个事件。#include"stm32f4xx_hal.h"//定义一个TIM_HandleTypeDef结构体TIM_HandleTypeDefhtim1;voidSystemClock_Config(void

轻量级软件FastGithub实现稳定访问github

当我们想访问全球最大的“同性交友网站”https://github.com/时,总会出现无法访问的界面,令人非常苦恼:幸运的是,有一种轻量级的软件可以帮助我们稳定地访问GitHub,那就是FastGithub。什么是FastGithub?FastGithub是一个简洁且专一的软件,它可以帮助你稳定地访问GitHub。F

深入浅出学Verilog--数据类型

1、数值类型在Verilog可以用4种数值来描述其构建的电路的电平逻辑,除了event类型和real类型外,几乎所有的数据类型都可以用这4种数值来表示。0:代表逻辑0,或者条件“假”1:代表逻辑1,或者条件“真”x或X:代表未知值。意味着不确定,可能是逻辑0,也可能是逻辑1。z或Z:代表高阻态,一般用于3态缓冲电路(t

【Linux】常用工具(下)

Linux常用工具一、Linux项目自动化构建工具-make/Makefile1.依赖关系和依赖方法2.伪目标3.make/Makefile具有依赖性的推导能力(语法扩展)4.编写一个进度条代码(1)缓冲区(2)\n和\r(3)进度条代码二、Linux版本控制器-git1.gitclone2.gitconfig3.gi

系统检测到您的账户不符合国家相关法律法规或《支付宝用户服务协议》约定,暂时无法签约当前产品

最新一直在开发支付宝小程序,遇到的各种问题颇多,技术上的问题都好解决,开发平台上的问题,真的是让我心力交瘁,自己分析不出原因,打支付宝客服电话永远得不到解答。现在把自己有一些收获的问题,分享给大家,作为抛砖引玉,大家有什么收获,我们也一起交流,让开发支付宝小程序的同行少走弯路。1,刚刚开的新号为什么不能签约签约首先要有

QT-day1作业

#include"mywnd.h"#include<iostream>#include<QDebug>#include<QIcon>#include<QPushButton>#include<QLabel>#include<QLineEdit>MyWnd::MyWnd(QWidget*parent):QWidget(p

知识图谱(4)图算法

基于图有很多任务,比如:节点分类:预测哪些网站是诈骗网站;关系预测:判断图中两个节点的关系;图分类:分子性质预测;聚类:社交网络分析,将相似用户聚类在一起,再推荐适合该簇的商品;图生成:药物分子生成,药物发现;目录图基础内容图遍历图聚类Node2Vec图基础内容节点的度:节点的边的数量。对于有向图,度还可以分为入度和出

植物大战僵尸各种僵尸攻略(四)

前言此文章为“植物大战僵尸”专栏中的011刊(2023年9月第十刊),欢迎订阅。版权所有。注意:1.本博客适用于pvz无名版;2.pvz指植物大战僵尸(PlantsVSZonbies);3.本文以耗费低做标准,方法不唯一;4.本期讲述难度较中型的僵尸。各种僵尸攻略潜水僵尸潜水僵尸有两种形态:第一种是普通形态;第二种是莲

热文推荐