[BZOJ1131] [POI2008]Sta
2016-02-01 21:23
267 查看
传送门
http://www.lydsy.com/JudgeOnline/problem.php?id=1131题目大意
给定一棵树,找到一个根,使所有点的深度和最大题解
树形DP我们先把这棵树处理成以1为根的有根树
维护以每个点为根的子树的节点数size[]size[]
我们逐层O(1)O(1)查询
设a=fa[b],且已知ans[a]a=fa[b],且已知ans[a]
那么从a为根转为b为根,b的子树中的点深度都−1,其他点深度都+1那么从a为根转为b为根,b的子树中的点深度都-1,其他点深度都+1
所以得到递推式ans[i]=ans[fa[i]]−size[i]+n−size[i]ans[i]=ans[fa[i]]-size[i]+n-size[i]
{$m 10000000} const maxn=1000005; var w:array[0..3*maxn,1..2]of longint; size,fa:array[0..maxn]of longint; ans:array[0..maxn]of int64; i,j,k:longint; n,m,len,a,b,anss:longint; procedure init(a,b:longint); begin w[len,1]:=b; if w[a,2]=0 then w[a,2]:=len else w[w[a,1],2]:=len; w[a,1]:=len; inc(len); end; procedure dfs1(a:longint); var tt:longint; begin size[a]:=1; tt:=w[a,2]; while tt<>0 do begin if w[tt,1]<>fa[a] then begin fa[w[tt,1]]:=a; dfs1(w[tt,1]); inc(size[a],size[w[tt,1]]); ans[a]:=ans[w[tt,1]]+size[w[tt,1]]; end; tt:=w[tt,2]; end; end; procedure dfs2(a:longint); var tt:longint; begin tt:=w[a,2]; if a<>1 then ans[a]:=ans[fa[a]]+n-size[a]-size[a]; while tt<>0 do begin if w[tt,1]<>fa[a] then dfs2(w[tt,1]); tt:=w[tt,2]; end; end; begin readln(n); len:=n+1; for i:=1 to n-1 do begin readln(a,b); init(a,b); init(b,a); end; dfs1(1); dfs2(1); anss:=0; ans[0]:=-1; for i:=1 to n do if ans[anss]<ans[i] then anss:=i; writeln(anss); end.
相关文章推荐
- git(二)
- textarea的换行符处理以及正确的在Html中显示
- 23种设计模式(2):工厂方法模式
- Spout的实现步骤
- YTU 2723: 默认参数--求圆的面积
- LeetCode——Search a 2D Matrix
- <Java设计模式>—UML类图
- 对数基础知识
- JavaScript数据类型
- 【leetcode】Power of Three
- hdu 2101 A + B Problem Too
- 算法题10 最长等差序列问题
- YTU 2720: 删出多余的空格
- 51nod 1174 区间中最大的数
- 字典补充
- bzoj3233 找硬币 动态规划&线性筛
- JavaScript——递归调用使用arguments.callee
- 最大可不连续的子段和(1087)
- JavaScript 中对小数取整的常用函数
- YTU 2715: 函数---判断某年某月某日是这一年中的第几天