51NOD 1424 零树
Discription
有一棵以1为根的树,他有n个结点,用1到n编号。第i号点有一个值vi。
现在可以对树进行如下操作:
步骤1:在树中选一个连通块,这个连通块必须包含1这个结点。
步骤2:然后对这个连通块中所有结点的值加1或者减1。
问最少要经过几次操作才能把树中所有结点都变成0。
注意:步骤1与步骤2合在一起为一次操作。
Input
单组测试数据。
第一行有一个整数n(1 ≤ n ≤ 10^5)
接下来n-1行,每行给出 ai 和 bi (1 ≤ ai, bi ≤ n; ai ≠ bi),表示ai和bi之间有一条边,输入保证是一棵树。
最后一行有n个以空格分开的整数,表示n个结点的值v1, v2, ..., vn (|vi| ≤ 10^9)。
Output
输出一个整数表示最少的操作步数。
Sample Input
3
1 2
1 3
1 -1 1
Sample Output
3
题解见注释(真的不知道我怎么想到差分约束的2333,网上全是用树上dp做的。。。)
/*
考虑差分约束。
1.设每个点i被add(i)次加操作涉及到,被dec(i)次减操作涉及到, 那么:
add(i) - dec(i) + w[i] = 0.
2.把dec用add表示后,每个点有两个限制:
(1). add(i) >= max{0,-w[i]}
(2). add(i) <= add(fa) + min{0,w[fa]-w[i]} 然后直接跑一个最短路,2*add(1) + w[1] 就是答案.
*/
#include<bits/stdc++.h>
#define ll long long
#define pb push_back
using namespace std;
const int maxn=100005;
vector<int> g[maxn];
int ne[maxn*5],to[maxn*5],num;
int hd[maxn],val[maxn*5],n,m,w[maxn];
bool iq[maxn];
ll d[maxn]; inline void add(int x,int y,int z){
to[++num]=y,ne[num]=hd[x],hd[x]=num,val[num]=z;
} void dfs(int x,int fa){
add(fa,x,min(0,w[fa]-w[x]));
for(int i=g[x].size()-1,TO;i>=0;i--){
TO=g[x][i];
if(TO==fa) continue;
dfs(TO,x);
}
} inline void build(){
for(int i=1;i<=n;i++) add(i,0,min(0,w[i]));
dfs(1,1);
} inline void spfa(){
queue<int> q;
for(int i=0;i<=n;i++) q.push(i),iq[i]=1;
int x;
while(!q.empty()){
x=q.front(),q.pop();
for(int i=hd[x];i;i=ne[i]) if(d[x]+(ll)val[i]<d[to[i]]){
d[to[i]]=d[x]+(ll)val[i];
if(!iq[to[i]]) q.push(to[i]),iq[to[i]]=1;
}
iq[x]=0;
}
for(int i=1;i<=n;i++) d[i]-=d[0];
} int main(){
scanf("%d",&n);
int uu,vv;
for(int i=1;i<n;i++){
scanf("%d%d",&uu,&vv);
g[uu].pb(vv),g[vv].pb(uu);
}
for(int i=1;i<=n;i++) scanf("%d",w+i); build();
spfa(); printf("%lld\n",d[1]*2+(ll)w[1]); return 0;
}
51NOD 1424 零树的更多相关文章
- 1424 零树 (树形DP)
1424 零树 题意 给出一棵树,每次可以选择一个包含节点 1 的连通块,将所有的节点的权值同时加 1 或减 1 ,问最少多少次操作使所有节点权值变为 0 . 分析 这种题意简单的题目好处就是能很快知 ...
- 51nod 1412 AVL树的种类(dp)
题目链接:51nod 1412 AVL树的种类 开始做的时候把深度开得过小了结果一直WA,是我天真了.. #include<cstdio> #include<cstring> ...
- 51nod 1412 AVL树的种类(经典dp)
http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1412 题意: 思路: 经典dp!!!可惜我想不到!! $dp[i][k] ...
- 51NOD 1353:树——题解
http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1353 今天小a在纸上研究树的形态,众所周知的,有芭蕉树,樟树,函树,平衡 ...
- 51nod 1287 线段树
http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1287 简单的线段树题目,直接写个二分查找大于等于x的最小位置就好了. # ...
- ACM学习历程—51NOD 1412 AVL树的种类(递推)
http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1770 这是这次BSG白山极客挑战赛的B题.设p(i, j)表示节点个数为 ...
- 【题解】彩色树 51nod 1868 虚树 树上dp
Prelude 题目在这里:ο(=•ω<=)ρ⌒☆ Solution 蒟蒻__stdcall的第一道虚树题qaq. 首先很容易发现,这个排列是假的. 我们只需要求出每对点之间的颜色数量,然后求个 ...
- 51nod 1819 黑白树V2(树链剖分)
第一次写如此复杂的树链剖分, 感觉自己代码能力还是挺不错的,没有调试太久(2个小时) 最后代码量高达11K orz(大部分都是重复的线段树代码,以后可以考虑优化一下代码量) 题解: 首先就是要进行一次 ...
- ACdream 1424 Diversion( 树链剖分 )
Diversion Time Limit: 2000/1000MS (Java/Others) Memory Limit: 128000/64000KB (Java/Others) Submit St ...
随机推荐
- Bootstrap历练实例:成功按钮
<!DOCTYPE html><html><head><meta http-equiv="Content-Type" content=&q ...
- iOS 第三方类库之MBProgressHUD
github链接地址 MBProgressHUD是一个开源的第三方类库实现了很多种样式的提示框,类似Activity indicator,使用上简单.方便,并且可以对显示的内容进行自定义,功能很强大, ...
- 学习笔记之30个常用的maven命令
maven 命令的格式为 mvn [plugin-name]:[goal-name],可以接受的参数如下, -D 指定参数,如 -Dmaven.test.skip=true 跳过单元测试: -P 指定 ...
- CSS实现跳动的桃心
又来刷题--CSS动画实现跳动的桃心,从哪里跌倒就从哪里爬起来,哈哈哈~ 分析:首先,得画出一个桃心,然后再用动画效果让它跳起来(关于动画,实在是弱项啊~~~,得补补了). 第一步:画桃心,思路是一个 ...
- Git学习——撤销修改
git checkout -- <file> 当你修改完一个工作区的文件后,使用git status查看当前的状态.其中有说明,接下来你可以git add <file> 去添加 ...
- 主DNS服务-反向解析
上篇说了主DNS正向解析 当中是有个小问题的,什么问题呢? 试问当我们输入wwww或ww或更多w的时候它还能解析出来吗? 或者不输入w的时候还能解析吗? 上篇没有定义是解析不了的,怎么定义呢?很简单, ...
- POJ:3461-Oulipo(KMP模板题)
原题传送:http://poj.org/problem?id=3461 Oulipo Time Limit: 1000MS Memory Limit: 65536K Description The F ...
- C# 反射总结
反射(Reflection)是.NET中的重要机制,通过放射,可以在运行时获得.NET中每一个类型(包括类.结构.委托.接口和枚举等)的成员,包括方法.属性.事件,以及构造函数等.还可以获得每个成员的 ...
- python算法-栈
定义: 栈(stack)又名堆栈,它是一种运算受限的线性表.其限制是仅允许在表的一端进行插入和删除运算.这一端被称为栈顶,相对地,把另一端称为栈底.向一个栈插入新元素又称作进栈.入栈或压栈,它是把新元 ...
- pycharm下多个工程项目并存显示
问题:使用pycharm新建一个工程时,出现如下提示: 无论选择哪一个,都会发现之前已经建立的工程没有并存显示 解决办法: 1. 找到file->settings: 2.点击project st ...