POI2014 FAR-FarmCraft
【Farm Craft】
【题目描述】
mhy住在一棵有n个点的树的1号结点上,每个结点上都有一个妹子。
mhy从自己家出发,去给每一个妹子都送一台电脑,每个妹子拿到电脑后就会开始安装zhx牌杀毒软件,第i个妹子安装时间为。
树上的每条边mhy能且仅能走两次,每次耗费1单位时间。mhy送完所有电脑后会回自己家里然后开始装zhx牌杀毒软件。
卸货和装电脑是不需要时间的。
求所有妹子和mhy都装好zhx牌杀毒软件的最短时间。
【Input】
第一行一个N,房屋数量
第二行N个数,C[i]
接下来的n - 1行表示相连接的房屋编号
【Output】
一个数字表示最少的时间
【Sample】
样例输入
6
1 8 9 6 3 2
1 3
2 3
3 4
4 5
4 6
样例输出
11
【Analyzation & Solution】
来看样例

模拟一下
1 3 2 3 4 5 4 6 4 3 1
此时time为10
再加上最后回到出发点的自己安装软件所需时间1
答案是11
可见,上述模拟是通过先走大的再走小的
这样的话能保证安装同时进行
那么这个贪心究竟对不对呢?
.png)
我们来看这个图
仅仅是把节点5的权值更改为了50
远远大于节点3的9
那么此时显然我们要先遍历5号节点才是最优
如果按照上述贪心一定是不成立的
那怎么办呢?

咳咳
模拟样例的过程中发现
每个节点都有两种决策
这不禁让人联想到了树型DP
定义f[i]表示遍历以i为根的子树最短所用时间
size[i]即当前子树的大小(边数)
引用某大佬の证明
假设u节点有儿子x和y,则如果先走x的话u的时间就为max(f[x]+1,f[y]+2*size[x]+1);
同理,先走 y 的话 u 的时间就为max(f[y]+1,f[x]+2*size[y]+1),若先安装x合适,则必有2*size[x]+f[y]+1>2*size[y]+f[x]+1,即f[x]-2*size[y]<f[y]-2*size[x]。
既然这样,我们排序 f[i] - size[i] 即可。
#include <iostream>
#include <cstring>
#include <cstdio>
#include <algorithm>
using namespace std;
inline int read(){
int x = 0, w = 1;
char ch = getchar();
for(; ch > '9' || ch < '0'; ch = getchar()) if(ch == '-') w = -1;
for(; ch >= '0' && ch <= '9'; ch = getchar()) x = x * 10 + ch - '0';
return x * w;
}
const int maxn = 500000+5;
int t, c[maxn], head[maxn], n, tot;
int f[maxn], size[maxn];
int q[maxn];
struct node{
int to,nxt;
}e[maxn << 1];
inline bool cmp(int x, int y){
return f[x] - 2 * size[x] > f[y] - 2 * size[y];
}
inline void add(int x, int y){
e[++tot].to = y;
e[tot].nxt = head[x];
head[x] = tot;
}
inline void dfs(int u, int fa){
int cnt=0, sum=1;
if(u == 1) f[u]=0;
else f[u] = c[u];
size[u] = 1;
for(int i = head[u]; i; i = e[i].nxt){
int v = e[i].to;
if(v == fa) continue;
dfs(v,u);
size[u] += size[v];
}
for(int i = head[u]; i; i = e[i].nxt)
if(e[i].to != fa)
q[++cnt] = e[i].to;
sort(q + 1, q +1 + cnt, cmp);
for(int i = 1; i <= cnt; i++){
f[u] = max(f[u], f[q[i]] + sum);
sum += 2 * size[q[i]];
}
}
int main(){
n = read();
for(int i = 1; i <= n; i++) c[i] = read();
for(int i = 1; i <= n - 1; i++){
int x = read(), y = read();
add(x, y);
add(y, x);
}
dfs(1, -1);
printf("%d", max(f[1], c[1] + 2 * (n - 1)));
return 0;
}
POI2014 FAR-FarmCraft的更多相关文章
- [补档][Poi2014]FarmCraft
[Poi2014]FarmCraft 题目 mhy住在一棵有n个点的树的1号结点上,每个结点上都有一个妹子. mhy从自己家出发,去给每一个妹子都送一台电脑,每个妹子拿到电脑后就会开始安装zhx牌杀毒 ...
- [BZOJ 3829][POI2014] FarmCraft
先贴一波题面... 3829: [Poi2014]FarmCraft Time Limit: 20 Sec Memory Limit: 128 MBSubmit: 421 Solved: 197[ ...
- 【BZOJ3829】[Poi2014]FarmCraft 树形DP(贪心)
[BZOJ3829][Poi2014]FarmCraft Description In a village called Byteville, there are houses connected ...
- FarmCraft[POI2014]
题目描述 In a village called Byteville, there are houses connected with N-1 roads. For each pair of ho ...
- BZOJ3829[Poi2014]FarmCraft——树形DP+贪心
题目描述 In a village called Byteville, there are houses connected with N-1 roads. For each pair of ho ...
- 【bzoj3829】[Poi2014]FarmCraft 贪心
原文地址:http://www.cnblogs.com/GXZlegend/p/6826667.html 题目描述 In a village called Byteville, there are ...
- [POI2014][树形DP]FarmCraft
题目 In a village called Byteville, there are houses connected with N-1 roads. For each pair of houses ...
- BZOJ3829 : [Poi2014]FarmCraft
d[x]表示走完x的子树并回到x所需的时间 f[x]表示从走到x开始计时,x子树中最晚的点安装完的最早时间 d[x]=sum(d[i]+2),i是x的孩子 f[x]的计算比较复杂: 考虑将x的各棵子树 ...
- [Poi2014]FarmCraft 树状dp
对于每个点,处理出走完其子树所需要的时间和其子树完全下载完软件的时间 易证,对于每个点的所有子节点,一定优先选择差值大的来给后面的时间 树规+贪心. #include<cstdio> #i ...
- BZOJ3829 [Poi2014]FarmCraft 【树形dp】
题目链接 BZOJ3829 题解 设\(f[i]\)为从\(i\)父亲进入\(i\)之前开始计时,\(i\)的子树中最晚装好的时间 同时记\(siz[i]\)为节点\(i\)子树大小的两倍,即为从父亲 ...
随机推荐
- 如何拿到阿里P8 Offer-候选人视角谈面试
自我介绍 首先简单自我介绍一下,我叫陈映平,花名叫做小卡,2011年校招进入腾讯,是腾讯课堂B侧的前端技术负责人.2015年响应总理的号召,跟朋友一起出来创业,跟前面一位讲师的经历有点像,然后2018 ...
- AntD框架的upload组件上传图片时使用customRequest方法自定义上传行为
本次做后台管理系统,采用的是 AntD 框架.涉及到图片的上传,用的是AntD的 upload 组件. 我在上一篇文章<AntD框架的upload组件上传图片时使用customRequest方法 ...
- v-model 指令来实现双向数据绑定
<div id="app"> <p>{{ message }}</p> <input v-model="message" ...
- Linux dd工具磁盘读写测试分析
话说,Linux 自带的dd工具测试硬盘读写速度只能提供一个大概的测试结果,而且是连续IO 而不是随机IO ,理论上文件规模越大,测试结果越准确.理论上bs越大,所测得性能越高. 上句来自网上,是不是 ...
- 用头发换JS的第一天
因为平时也在上班,这些都是在地铁上抽空开始看的,总结来说还是有一些收获存在,每次看都能发现一些新东西,废话不多说,开撸! JavaScript是一种网页编程语言,可以对网页的行为进行编程,简单来说HT ...
- .Net Core微服务入门全纪录(三)——Consul-服务注册与发现(下)
前言 上一篇[.Net Core微服务入门全纪录(二)--Consul-服务注册与发现(上)]已经成功将我们的服务注册到Consul中,接下来就该客户端通过Consul去做服务发现了. 服务发现 同样 ...
- Linux服务器安装python3.6
CentOS 7上默认安装的python版本是2.7.5,系统自带的旧版本python被系统很多其他软件环境依赖,因此不能卸载原Python,直接选择Python3.6.5进行全新安装. 1 安装Py ...
- 论logstash的玩法(ELK)
本篇文章采用的采用的是logstash-7.7.0版本,主要从如下几个方面介绍 1.logstash是什么,可以用来干啥 2.logstash的基本原理是什么 3.怎么去玩这个elk的组件logsta ...
- 深入理解Java虚拟机学习笔记(三)-----类文件结构/虚拟机类加载机制
第6章 类文件结构 1. 无关性 各种不同平台的虚拟机与所有平台都统一使用的程序存储格式——字节码(即扩展名为 .class 的文件) 是构成平台无关性的基石. 字节码(即扩展名为 .class 的文 ...
- 小师妹学JVM之:JIT中的LogCompilation
目录 简介 LogCompilation简介 LogCompilation的使用 解析LogCompilation文件 总结 简介 我们知道在JVM中为了加快编译速度,引入了JIT即时编译的功能.那么 ...