HDU - 6133 启发式合并
题意:给出一棵树共\(n\)个顶点,每个顶点有一个权值\(val_i\),你需要对每个节点统计一个最优解
每个节点的解按照一定规则产生:取出该节点的子树下所有的顶点,把顶点任意排序成一个序列,设为\(v_1,v_2...,v_k\)
此时解为\(\sum_{i=1}^{k}\sum_{j=1}^{i}val_{v_j}\),最小的解为最优解
对于每个解的处理来说,子树下值小的顶点肯定放前面,按这样来贪心无疑是正确的(前缀贡献尽量小)
那么对于无序的插入过程,当前节点\(u\)的贡献为\(val_u+cnt+num*val_u\)
其中\(cnt\)为当前小于\(val_u\)的数字和,\(num\)为当前大于等于\(val_u\)的个数和
因为是子树问题,用树状数组暴力合并答案,复杂度\(O(nlog^2n)\)
#include<bits/stdc++.h>
#define rep(i,j,k) for(register int i=j;i<=k;i++)
#define rrep(i,j,k) for(register int i=j;i>=k;i--)
#define print(a) printf("%lld",(ll)a)
#define println(a) printf("%lld\n",(ll)a)
#define printbk(a) printf("%lld ",(ll)a)
#define IOS ios::sync_with_stdio(0)
using namespace std;
const int MAXN = 2e6+11;
typedef long long ll;
ll read(){
ll x=0,f=1;register char ch=getchar();
while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();}
return x*f;
}
ll a[MAXN],b[MAXN],c[MAXN];
int to[MAXN<<1],nxt[MAXN<<1],head[MAXN],tot;
void add(int u,int v){
to[tot]=v;
nxt[tot]=head[u];
head[u]=tot++;
}
struct FT{
ll ft[MAXN];
int tot;
void init(int t){for(tot=t=t<<1|1;t;--t)ft[t]=0;}
#define lowbit(x) (x&-x)
void update(int k,int v){while(k<tot)ft[k]+=v,k+=lowbit(k);}
ll query(int k){return k>0?ft[k]+query(k-lowbit(k)):0;}
}ft[2];
int size[MAXN],son[MAXN],st[MAXN],ed[MAXN],pre[MAXN],CLOCK;
void init(){
memset(head,-1,sizeof head);
tot=CLOCK=0;
}
void dfs(int u,int fa){
size[u]=1;son[u]=0;
st[u]=++CLOCK;pre[CLOCK]=u;
for(int i=head[u];~i;i=nxt[i]){
int v=to[i];
if(v==fa) continue;
dfs(v,u);
size[u]+=size[v];
if(size[v]>size[son[u]]) son[u]=v;
}
ed[u]=CLOCK;
}
ll ans[MAXN];
void solve(int u,int fa,bool keep){
for(int i=head[u];~i;i=nxt[i]){
int v=to[i];
if(v==fa) continue;
if(v==son[u]) continue;
solve(v,u,0);
}
if(son[u]) solve(son[u],u,1);
ll t=ans[son[u]];
for(int i=head[u];~i;i=nxt[i]){
int v=to[i];
if(v==fa) continue;
if(v==son[u]) continue;
rep(j,st[v],ed[v]){
t+=a[pre[j]];
t+=ft[0].query(c[pre[j]]-1);
ft[0].update(c[pre[j]],a[pre[j]]);
t+=(ft[1].query(ft[1].tot)-ft[1].query(c[pre[j]]-1))*a[pre[j]];
ft[1].update(c[pre[j]],1);
}
}
t+=a[u];
t+=ft[0].query(c[u]-1);
ft[0].update(c[u],a[u]);
t+=(ft[1].query(ft[1].tot)-ft[1].query(c[u]-1))*a[u];
ft[1].update(c[u],1);
ans[u]=t;
if(!keep) rep(j,st[u],ed[u]){
ft[0].update(c[pre[j]],-a[pre[j]]);
ft[1].update(c[pre[j]],-1);
}
}
int main(){
int T=read();
while(T--){
int n=read();
rep(i,1,n) b[i]=a[i]=read();
sort(b+1,b+1+n);
int m=unique(b+1,b+1+n)-b-1;
rep(i,1,n) c[i]=lower_bound(b+1,b+1+n,a[i])-b;
rep(i,0,1) ft[i].init(max(n,m));
init();
rep(i,1,n-1){
int u=read();
int v=read();
add(u,v);
add(v,u);
}
memset(ans,0,sizeof ans);
dfs(1,-1);
solve(1,-1,1);
rep(i,1,n) printbk(ans[i]); puts("");
}
return 0;
}
HDU - 6133 启发式合并的更多相关文章
- hdu 3371(启发式合并的最小生成树)
Connect the Cities Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Other ...
- HDU 5029 Relief grain(离线+线段树+启发式合并)(2014 ACM/ICPC Asia Regional Guangzhou Online)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5029 Problem Description The soil is cracking up beca ...
- [HDU 3712] Fiolki (带边权并查集+启发式合并)
[HDU 3712] Fiolki (带边权并查集+启发式合并) 题面 化学家吉丽想要配置一种神奇的药水来拯救世界. 吉丽有n种不同的液体物质,和n个药瓶(均从1到n编号).初始时,第i个瓶内装着g[ ...
- 数据结构(trie,启发式合并):HDU 5841 Alice and Bob
aaarticlea/png;base64,iVBORw0KGgoAAAANSUhEUgAABJEAAAE6CAIAAAApz1RvAAAgAElEQVR4nO3d3css1b3g8fyTdbHJbD
- hdu 6133---Army Formations(启发式合并+树状数组)
题目链接 Problem Description > Stormtroopers were the assault/policing troops of the Galactic Empire. ...
- HDU 5877 2016大连网络赛 Weak Pair(树状数组,线段树,动态开点,启发式合并,可持久化线段树)
Weak Pair Time Limit: 4000/2000 MS (Java/Others) Memory Limit: 262144/262144 K (Java/Others) Tota ...
- Problem E. TeaTree - HDU - 6430 (树的启发式合并)
题意 有一棵树,每个节点有一个权值. 任何两个不同的节点都会把他们权值的\(gcd\)告诉他们的\(LCA\)节点.问每个节点被告诉的最大的数. 题解 第一次接触到树的启发式合并. 用一个set维护每 ...
- HDU - 4358 Boring counting (树上启发式合并/线段树合并)
题目链接 题意:统计树上每个结点中恰好出现了k次的颜色数. dsu on tree/线段树合并裸题. 启发式合并1:(748ms) #include<bits/stdc++.h> usin ...
- [bzoj3123][sdoi2013森林] (树上主席树+lca+并查集启发式合并+暴力重构森林)
Description Input 第一行包含一个正整数testcase,表示当前测试数据的测试点编号.保证1≤testcase≤20. 第二行包含三个整数N,M,T,分别表示节点数.初始边数.操作数 ...
随机推荐
- Java Thread系列(二)线程状态
Java Thread系列(二)线程状态 一.线程的五种状态 新建状态(New):新创建了一个线程对象,尚未启动. 就绪状态(Runnable):也叫可运行状态.线程对象创建后,其他线程调用了该对象的 ...
- 14 Finding a Shared Motif
Problem A common substring of a collection of strings is a substring of every member of the collecti ...
- loadrunner - Run time Settings 的详细说明
本文主要讲解一下run-time settings(如图1所示)里各设置项的具体含义(注:标红色的选项卡是比较值得关注的,可重点看一下): 图1 1.General / Run Logic 选项卡 ...
- loadrunner - 安装与破解
最近准备学习LR,借助这个平台,将自己的学习经历记录下来,当然很多都不是原创,都是遇到问题时各种百度,然后梳理下知识是为了避免以后遇到同样的错误时,能回过头来参考参考. 下面的是转载某位大神的博客,尊 ...
- ADO接口之_RecordsetPtr
转自:http://hi.baidu.com/%CE%D2%B6%CF%C1%CB%CB%BC%C4%EE/blog/item/e057c526c6af6c29c995596e.html _Recor ...
- Quartus II 软件生成FFT、NCO、FIR等IP核时卡住不动的解决办法
据网友表示,遇到这个问题时,在任务管理器中手动关闭quartus_map进程就可以了,由于我的电脑最近一直没有出问题,因此也无法验证.欢迎大家针对这个问题讨论,提出肯定.否定的说法. 另外,很多人表示 ...
- handsontable-cell type
在单元格中呈现自定义的元素:不能使用html元素 var data = [ { title: "<a href='http://www.amazon.com/Professional- ...
- 介绍自己,并介绍github注册过程和初步使用
我是一名南通大学的学生,我叫李可,学号是1413042029,班级:网络工程141,我是一名网络工程专业的学生,我一般喜欢看看课外书. 现在我介绍一下我注册github的过程: 1.登陆https:/ ...
- akka 练手 原来第一次是原封不动的返回传出去的参数
今天,有介绍akka的文章,就下了个源码的demo练手! 在TimeServer 这个实例中主要就2个文件 server端 static void Main(string[] args) { usin ...
- 目前主流的四大浏览器内核Trident、Gecko、WebKit以及Presto
“浏览器内核”主要指渲染引擎(Rendering Engine),负责解析网页语法(如HTML.JavaScript)并渲染.展示网页.因此,所谓的浏览器内核通常也就是指浏览器所采用的渲染引擎,渲染引 ...