2018.07.22哨戒炮 II(树形dp)
哨戒炮 II
描述
你的防线成功升级,从原来的一根线变成了一棵树。这棵树有 N 个炮台,炮台与炮台之间 有 N-1 条隧道。你要选择一些炮台安装哨戒炮。在第 i 个炮台上安装哨戒炮得到的防御力为 vi。上次说过,哨戒炮离得太近会产生神奇的效果。具体来说,对于炮台 i,如果它安装了 哨戒炮且和 k 个哨戒炮用隧道直接相连,那么其防御力会变化 k*di。其中 di 为炮台 i 的抗 干扰属性值。如果为正,干扰对其有正的作用;为负,干扰对其有负的作用;为 0,则完全 不受干扰。
你的整套防线的防御力为所有哨戒炮的防御力之和。求防线的最大防御力
输入
第一行一个整数 N,表示炮台数量。
第二行 N 个整数表示 vi。
第三行 N 个整数表示 di。
接下来 N-1 行每行两个整数描述一条隧道。
输出
输出一行一个整数表示答案
样例输入
2
1 1
0 0
1 2
样例输出
2
提示
对于 20%的数据,N <= 20。
对于 40%的数据,N <= 100。
对于 70%的数据,N <= 5000。
对于 100%的数据,N <= 100000
这题杠了40min然后发现读优写挂了。
事实上状态转移方程最开始推对了啊233。。。
不难看出这是一道树形dp" role="presentation" style="position: relative;">dpdp。
我们用fi,0/1" role="presentation" style="position: relative;">fi,0/1fi,0/1表示当前在标号为i" role="presentation" style="position: relative;">ii的节点,当前节点安放哨戒炮/没有安放哨戒炮。
然后dfs" role="presentation" style="position: relative;">dfsdfs的时候用一点小技巧(瞎yy" role="presentation" style="position: relative;">yyyy的),就是每次dfs" role="presentation" style="position: relative;">dfsdfs的时候并不考虑题目中说的di" role="presentation" style="position: relative;">didi的影响,而是将这个影响转移给儿子,比如说,我们当前选了u" role="presentation" style="position: relative;">uu,然后准备从选择儿子v" role="presentation" style="position: relative;">vv的情况向当前情况转移,就可以在这一层dfs" role="presentation" style="position: relative;">dfsdfs的时候放弃计算d[p]" role="presentation" style="position: relative;">d[p]d[p]这个东西,而是在dfs" role="presentation" style="position: relative;">dfsdfs儿子v" role="presentation" style="position: relative;">vv的时候附加一个值sum" role="presentation" style="position: relative;">sumsum,在v" role="presentation" style="position: relative;">vv递归返回的时候加上这个值就行了。
但sum" role="presentation" style="position: relative;">sumsum的值如何计算呢?于是我们分情况考虑。
如果当前点u" role="presentation" style="position: relative;">uu没有被选,那么对儿子没有影响,因此无论儿子选还是不选,sum" role="presentation" style="position: relative;">sumsum值都为0" role="presentation" style="position: relative;">00。
那如果u" role="presentation" style="position: relative;">uu被选了呢?如果儿子不选,sum" role="presentation" style="position: relative;">sumsum值仍然为0" role="presentation" style="position: relative;">00,而如果儿子被选,显然总答案的值会加上d[u]+d[v]" role="presentation" style="position: relative;">d[u]+d[v]d[u]+d[v],因此sum" role="presentation" style="position: relative;">sumsum的值就等于d[u]+d[v]" role="presentation" style="position: relative;">d[u]+d[v]d[u]+d[v]。
这样一来可以轻松地写出状态转移方程了。
f[u][0]=∑max(f[v][0],f[v][1])" role="presentation" style="position: relative;">f[u][0]=∑max(f[v][0],f[v][1])f[u][0]=∑max(f[v][0],f[v][1])
f[u][1]=∑max(f[v][0],f[v][1]+d[u]+d[v])" role="presentation" style="position: relative;">f[u][1]=∑max(f[v][0],f[v][1]+d[u]+d[v])f[u][1]=∑max(f[v][0],f[v][1]+d[u]+d[v])
这样还是不够,要记得只有安放了哨戒炮的位置才能获得防御力v[i]" role="presentation" style="position: relative;">v[i]v[i],因此第二个状态转移方程事实上是错的。
应该是:f[u][1]=∑(max(f[v][0],f[v][1]+d[u]+d[v])+V[u])" role="presentation" style="position: relative;">f[u][1]=∑(max(f[v][0],f[v][1]+d[u]+d[v])+V[u])f[u][1]=∑(max(f[v][0],f[v][1]+d[u]+d[v])+V[u])
代码如下:
#include<bits/stdc++.h>
#define N 100005
#define ll long long
using namespace std;
ll dp[N][2],n,a[N],d[N],cnt=0,first[N];
struct Node{ll v,next;}e[N<<1];
inline ll read(){
ll ans=0,w=1;
char ch=getchar();
while(!isdigit(ch)){if(ch=='-')w=-1;ch=getchar();}
while(isdigit(ch))ans=(ans<<3)+(ans<<1)+(ch^48),ch=getchar();
return ans*w;
}
inline ll dfs(ll p,ll f,ll sum,ll fa){
if(dp[p][f]!=-1)return dp[p][f]+sum;
dp[p][f]=0;
if(f==0){
for(ll i=first[p];i;i=e[i].next){
ll v=e[i].v;
if(v==fa)continue;
dp[p][f]+=max(dfs(v,0,0,p),dfs(v,1,0,p));
}
return dp[p][f]+sum;
}
dp[p][f]=d[p];
for(ll i=first[p];i;i=e[i].next){
ll v=e[i].v;
if(v==fa)continue;
dp[p][f]+=max(dfs(v,0,0,p),dfs(v,1,a[p]+a[v],p));
}
return dp[p][f]+sum;
}
inline void add(ll u,ll v){e[++cnt].v=v,e[cnt].next=first[u],first[u]=cnt;}
int main(){
memset(dp,-1,sizeof(dp));
n=read();
for(ll i=1;i<=n;++i)d[i]=read();
for(ll i=1;i<=n;++i)a[i]=read();
for(ll i=1;i<n;++i){
ll u=read(),v=read();
add(u,v),add(v,u);
}
printf("%lld",max(dfs(1,0,0,1),dfs(1,1,0,1)));
return 0;
}
2018.07.22哨戒炮 II(树形dp)的更多相关文章
- 2021.07.17 P3177 树上染色(树形DP)
2021.07.17 P3177 树上染色(树形DP) [P3177 HAOI2015]树上染色 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn) 重点: 1.dp思想是需要什么,维护 ...
- [SHOI2008]仙人掌图 II——树形dp与环形处理
题意: 给定一个仙人掌,边权为1 距离定义为两个点之间的最短路径 直径定义为距离最远的两个点的距离 求仙人掌直径 题解: 类比树形dp求直径. f[i]表示i向下最多多长 处理链的话,直接dp即可. ...
- 2019.02.07 bzoj4784: [Zjoi2017]仙人掌(仙人掌+树形dp)
传送门 题意:给一个无向连通图,问给它加边形成仙人掌的方案数. 思路: 先考虑给一棵树加边形成仙人掌的方案数. 这个显然可以做树形dp. fif_ifi表示把iii为根的子树加边形成仙人掌的方案数. ...
- 2018.07.22 洛谷P3047附近的牛(树形dp)
传送门 给出一棵n" role="presentation" style="position: relative;">nn个点的树,每个点上有C ...
- 2018.07.22 洛谷P2986 伟大的奶牛聚集(树形dp)
传送门 给出一棵树,树有边权和点权,若选定一个点作为中心,这棵树的代价是所有点权乘上到根的距离的和.求代价最小. 解法:一道明显的换根dp" role="presentation& ...
- 2018.07.22 codeforces750E(线段树维护状态转移)
传送门 给出一个数字字串,给出若干个询问,询问在字串的一段区间保证出现2017" role="presentation" style="position: re ...
- 2018.07.22 洛谷P4316 绿豆蛙的归宿(概率dp)
传送门 简单的递推. 由于是DAG" role="presentation" style="position: relative;">DAGDA ...
- 2018.07.22 洛谷P1967 货车运输(kruskal重构树)
传送门 这道题以前只会树剖和最小生成树+倍增. 而现在学习了一个叫做kruskal" role="presentation" style="position: ...
- 2018.07.22 洛谷P3106 GPS的决斗Dueling GPS's(最短路)
传送门 图论模拟题. 这题直接写3个(可以压成一个)spfa" role="presentation" style="position: relative;&q ...
随机推荐
- Java实现邮箱发送
- django celery 定时任务
可参考上一篇:http://www.cnblogs.com/wumingxiaoyao/p/8515075.html 1. 安装 django-celery-beat pip3 install dja ...
- Mysql binlog二进制日志
Mysql binlog日志有三种格式,分别为Statement,MiXED,以及ROW! 1.Statement:每一条会修改数据的实际原sql语句都会被记录在binlog中. 优点:不需要记录每一 ...
- Haskell语言学习笔记(42)Bifunctor
Bifunctor class Bifunctor p where bimap :: (a -> b) -> (c -> d) -> p a c -> p b d bim ...
- 【336】Tutorial of Endnote
Now I start to use Endnote to manage my literatures and I need to learn how to use it. Below is some ...
- IOS6新特性之下拉刷新<UIRefreshControl>
在IOS6未发布之前,几乎都是使用那个UIRefresh在实现下拉刷新,甚至有人还是先了上拉的功能,不得不说牛人很多啊.可能是Apple意识到了这个功能的实用性,在IOS6中增加了下拉刷新,但是上啦还 ...
- spark cache table
http://www.07net01.com/2015/11/961118.html http://www.cnblogs.com/charlotte77/p/5468968.html 文本读入和写出 ...
- git cherry-pick用法
场景: 如果你的应用已经发布了一个版本2.0, 代码分支叫release-2.0, 现在正在开发3.0, 代码的分支叫dev-3.0. 那么有一天产品说, 要把正在开发的某个特性提前上线, 也就是说要 ...
- TOMCAT Note: further occurrences of HTTP header parsing errors will be logged at DEBUG level.
十二月 31, 2014 2:32:45 下午 org.apache.coyote.http11.AbstractHttp11Processor process信息: Error parsing HT ...
- 视图的URL配置,找不到我设置的第一个Page
问题:视图的URL配置,找不到我设置的第一个Page 我的代码如下: 结果访问/test/时说找不到这个page 原因:patterns方法的参数有两个,一个是prefix,一个是参数元祖,详见下 ...