标签:des blog http io os ar java for strong
Time Limit: 10000/5000 MS (Java/Others) Memory Limit: 65536/65536 K (Java/Others)
Total Submission(s): 442 Accepted Submission(s): 122
思路:lct or 树链分割
调了三天,终于过了,。。。不容易呀。。。
#pragma comment(linker, "/STACK:102400000,102400000")
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<queue>
#include<vector>
#include<set>
#include<stack>
#include<map>
#include<ctime>
#include<bitset>
#define LL long long
#define INF 999999
#define mod 20140518
#define maxn 50010
using namespace std;
int head[maxn],next1[maxn*2],to[maxn*2] ;
int top1 ;
bool vi[maxn] ;
struct node
{
int Max,Min;
int add,lans,rans;
}tree[maxn*3],num[maxn];
int ql,qr,val ;
node vv ;
int max(int x,int y ){return x > y?x:y;}
int min(int x,int y ){return x < y?x:y;}
void Unit(int u,int v )
{
next1[top1] = head[u] ;to[top1] = v ;
head[u] = top1++;
}
void up(int o )
{
tree[o].Max = max(tree[o<<1].Max,tree[o<<1|1].Max) ;
tree[o].Min = min(tree[o<<1].Min,tree[o<<1|1].Min) ;
tree[o].lans = max(tree[o<<1].lans,tree[o<<1|1].lans) ;
tree[o].lans = max(tree[o].lans,tree[o<<1].Max-tree[o<<1|1].Min) ;
tree[o].rans = max(tree[o<<1].rans,tree[o<<1|1].rans) ;
tree[o].rans = max(tree[o].rans,tree[o<<1|1].Max-tree[o<<1].Min) ;
}
void Add(int o ,int add)
{
tree[o].add += add ;
tree[o].Max += add ;
tree[o].Min += add ;
}
void down(int o )
{
if(tree[o].add)
{
Add((o<<1),tree[o].add) ;
Add((o<<1|1),tree[o].add) ;
tree[o].add = 0;
}
}
void insert(int L,int R,int o )
{
tree[o].add=0;
if(L==R)
{
tree[o] = num[L] ;
return ;
}
int mid=(L+R)>>1 ;
insert(L,mid,o<<1) ;
insert(mid+1,R,o<<1|1) ;
up(o) ;
}
void update(int L,int R,int o )
{
if(ql <= L && qr >= R)
{
Add(o,val) ;
return ;
}
down(o) ;
int mid=(L+R)>>1 ;
if(ql <= mid)update(L,mid,o<<1) ;
if(qr > mid) update(mid+1,R,o<<1|1) ;
up(o);
}
void find(int L,int R,int o,node &c )
{
if(ql <= L && qr >= R)
{
c = tree[o] ;
return ;
}
int mid=(L+R)>>1 ;
down(o) ;
if(ql > mid)
{
find(mid+1,R,o<<1|1,c) ;
return ;
}
else if(qr <= mid)
{
find(L,mid,o<<1,c) ;
return ;
}
node a ;
find(L,mid,o<<1,a) ;
node b ;
find(mid+1,R,o<<1|1,b) ;
c.Max = max(a.Max,b.Max) ;
c.Min = min(a.Min,b.Min) ;
c.lans = max(a.lans,max(a.Max-b.Min,b.lans)) ;
c.rans = max(a.rans,max(b.Max-a.Min,b.rans)) ;
}
int w[maxn],fa[maxn],top[maxn],sz ;
int size1[maxn],son[maxn] ,dep[maxn];
void init()
{
memset(w,0,sizeof(w));
memset(size1,0,sizeof(size1)) ;
memset(dep,0,sizeof(dep)) ;
memset(son,0,sizeof(son)) ;
memset(top,0,sizeof(top)) ;
memset(fa,0,sizeof(fa)) ;
}
void dfs(int u)
{
size1[u] = 1 ;son[u] = 0 ;
for(int i = head[u] ; i != -1 ; i = next1[i])
{
int v = to[i] ;
if(v==fa[u]) continue ;
fa[v]=u;
dep[v] = dep[u]+1;
dfs(v) ;
if(size1[v] > size1[son[u]])
son[u] = v ;
size1[u] += size1[v] ;
}
}
void build(int u,int t)
{
top[u] = t ;
w[u] = ++sz ;
if(son[u]) build(son[u],t) ;
for(int i = head[u] ; i != -1 ; i = next1[i])
{
int v = to[i] ;
if(v==fa[u]||v==son[u]) continue ;
build(v,v) ;
}
}
int query(int u,int v )
{
int f1,f2,flag=0,ans=0;
node a[2],b,c,d;
f1 = top[u] ;
f2 = top[v] ;
a[0].Max=a[1].Max=-1;
while(f1 != f2)
{
// puts("==========");
if(dep[f1] < dep[f2])
{
swap(f1,f2) ;
swap(u,v) ;
flag ^= 1;
}
ql = w[f1] ;qr = w[u] ;
u = fa[f1] ;f1=top[u] ;
find(1,sz,1,d) ;
if(a[flag].Max==-1)
{
a[flag] = d ;
continue ;
}
b = d ;
d = a[flag] ;
c.Max = max(d.Max,b.Max) ;
c.Min = min(d.Min,b.Min) ;
c.lans = max(d.lans,max(b.Max-d.Min,b.lans)) ;
c.rans = max(d.rans,max(d.Max-b.Min,b.rans)) ;
if(flag) ans = max(ans,c.rans) ;
else ans = max(ans,c.lans);
a[flag] = c ;
}
if(dep[u] < dep[v])
{
swap(u,v) ;
flag ^= 1;
}
ql = w[v] ; qr = w[u] ;
find(1,sz,1,d) ;
if(a[flag].Max!=-1){
b = d ;
d = a[flag] ;
c.Max = max(d.Max,b.Max) ;
c.Min = min(d.Min,b.Min) ;
c.lans = max(d.lans,max(b.Max-d.Min,b.lans)) ;
c.rans = max(d.rans,max(d.Max-b.Min,b.rans)) ;
if(flag) ans = max(ans,c.rans) ;
else ans = max(ans,c.lans);
a[flag] = c ;
}
else a[flag] = d ;
if(a[0].Max==-1)
{
return max(ans,a[1].rans) ;
}
else if(a[1].Max==-1)
{
// puts("-----------");
// // cout << a[0].lans << "==" << a[0].rans << endl;
return max(ans,a[0].lans) ;
}
ans = max(ans,a[1].rans);
ans = max(ans,a[0].lans);
ans = max(ans,a[1].Max-a[0].Min);
return ans;
}
void ADD(int u,int v ,int c )
{
int f1,f2;
f1 = top[u];f2=top[v] ;
val = c ;
while(f1 != f2)
{
if(dep[f1] < dep[f2])
{
swap(f1,f2) ;
swap(u,v) ;
}
ql=w[f1] ;qr=w[u] ;
u = fa[f1] ;
f1 = top[u] ;
update(1,sz,1) ;
}
if(dep[u] >dep[v])
swap(u,v) ;
ql = w[u];qr=w[v] ;
update(1,sz,1);
}
int next_int() {
char c;
int re = 0;
c = getchar();
while (c < ‘0‘ || c > ‘9‘) c = getchar();
while (c >= ‘0‘ && c <= ‘9‘) {
re = re*10+c-‘0‘;
c = getchar();
}
return re;
}
int ee[maxn] ;
int main()
{
int n,m,x,y,i,j;
int T,c ;
//freopen("in.txt","r",stdin);
scanf("%d",&T);
while( T-- )
{
n = next_int();
memset(head,-1,sizeof(head)) ;
top1=0;
for( i = 1 ; i <= n ;i++)
{
// scanf("%d",&ee[i]) ;
ee[i]=next_int();
}
for( i = 1 ; i < n ;i++)
{
// scanf("%d%d",&x,&y) ;
x = next_int();
y = next_int();
Unit(x,y) ;
Unit(y,x) ;
}
sz=0;
init();
dfs(1) ;
build(1,1);
for( i = 1 ; i <= n ;i++)
{
ql=w[i];
vv.Max = ee[i];
vv.Min = ee[i] ;
vv.lans = vv.rans = 0;
num[ql] = vv ;
}
insert(1,sz,1);
m = next_int();
while(m--)
{
// scanf("%d%d%d",&x,&y,&c) ;
x = next_int();
y = next_int();
c = next_int();
printf("%d\n",query(x,y)) ;
ADD(x,y,c) ;
}
}
return 0 ;
}
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<queue>
#include<vector>
#include<set>
#include<stack>
#include<map>
#include<ctime>
#include<bitset>
#define LL long long
#define INF 999999
#define mod 20140518
#define maxn 100010
using namespace std;
int head[maxn],next1[maxn*2],to[maxn*2] ;
int top ,n ;
bool vi[maxn] ;
void Unit(int u,int v )
{
next1[top] = head[u] ;to[top] = v ;
head[u] = top++;
}
struct LCT
{
int w[maxn],add[maxn],Max[maxn];
int ch[maxn][2],pre[maxn] ;
int L[maxn] ;
int Min[maxn],ans[maxn] ;
bool rev[maxn] ;
void init()
{
memset(rev,0,sizeof(rev)) ;
memset(ch,0,sizeof(ch)) ;
memset(add,0,sizeof(add));
memset(pre,0,sizeof(pre)) ;
memset(Max,0,sizeof(Max)) ;
memset(ans,0,sizeof(ans)) ;
memset(Min,0,sizeof(Min)) ;
memset(L,0,sizeof(L)) ;
}
void Add(int x ,int val)
{
if(x)
{
add[x] += val ;
w[x] += val ;
Max[x] += val ;
Min[x] += val ;
}
}
void update(int x )
{
Max[x] = max(w[x],max(Max[ch[x][0]],Max[ch[x][1]])) ;
Min[x] = w[x];
if(ch[x][1]) Min[x] = min(Min[ch[x][1]],Min[x]) ;
if(ch[x][0]) Min[x] = min(Min[ch[x][0]],Min[x]) ;
ans[x] = max(ans[ch[x][0]],max(0,ans[ch[x][1]])) ;
if(ch[x][0]&&ch[x][1])ans[x] = max(ans[x],Max[ch[x][0]]-Min[ch[x][1]]) ;
if(ch[x][0])ans[x] = max(ans[x],Max[ch[x][0]]-w[x]) ;
if(ch[x][1])ans[x] = max(ans[x],w[x]-Min[ch[x][1]]) ;
L[x] = max(L[ch[x][0]],max(0,L[ch[x][1]])) ;
if(ch[x][0]&&ch[x][1])L[x] = max(L[x],Max[ch[x][1]]-Min[ch[x][0]]) ;
if(ch[x][1])L[x] = max(L[x],Max[ch[x][1]]-w[x]) ;
if(ch[x][0])L[x] = max(L[x],w[x]-Min[ch[x][0]]) ;
}
void down(int x )
{
if(add[x])
{
Add(ch[x][0],add[x]) ;
Add(ch[x][1],add[x]) ;
add[x]=0;
}
return ;
if(rev[x])
{
swap(ch[x][0],ch[x][1]) ;
rev[ch[x][0]] ^= 1;
rev[ch[x][1]] ^= 1;
rev[x] = 0;
}
}
bool isroot(int x )
{
if(ch[pre[x]][0] != x && ch[pre[x]][1] != x )
return true ;
return false;
}
void pushdown(int x )
{
if(!isroot(x)) pushdown(pre[x]) ;
down(x) ;
}
void rotate(int x,int f)
{
int y = pre[x],z = pre[y];
ch[y][!f] = ch[x][f];
pre[ ch[x][f] ] = y;
pre[x] = pre[y];
if(ch[z][0] == y)ch[z][0] = x;
else if(ch[z][1] == y)ch[z][1] = x;
pre[y] = x;
ch[x][f] = y;
update(y);
}
void splay(int x)
{
pushdown(x);
while(!isroot(x))
{
if(isroot(pre[x]))rotate(x,ch[pre[x]][0] == x);
else
{
int y = pre[x],z = pre[y];
int f = (ch[z][0] == y);
if(ch[y][f] == x)rotate(x,!f),rotate(x,f);
else rotate(y,f),rotate(x,f);
}
}
update(x);
}
void access(int u)
{
for(int f = 0 ; u ;u = pre[u])
{
splay(u);
ch[u][1] = f ;
update(u);
f = u ;
}
}
bool check(int a ,int b)
{
int x =a,y=b;
access(y) ;
for(int f = 0 ;x ;x = pre[x])
{
splay(x) ;
if(!pre[x]) break ;
f = x ;
}
for( ; ch[x][1] ; x = ch[x][1]);
return x == b ;
}
void make_root(int x )
{
access(x) ;
splay(x) ;
rev[x] ^= 1;
}
void cut(int x,int y )
{
if(x==y||!check(x,y))
{
puts("-1") ;
return ;
}
make_root(x) ;
splay(y) ;
pre[ch[y][0]] = pre[y] ;
pre[y] = ch[y][0] = 0 ;
}
int find(int x,int y )
{
access(y) ;
for( int f = 0 ; x ; x = pre[x])
{
splay(x) ;
if(!pre[x])
{
int Max1 = 0 ;
Max1 = max(ans[f],L[ch[x][1]]);
if(ch[x][1])Max1 = max(Max1,Max[ch[x][1]]-w[x]) ;
if(f)Max1 = max(Max1,w[x]-Min[f]) ;
if(ch[x][1]&&f) Max1= max(Max1,Max[ch[x][1]]-Min[f]);
return Max1;
}
ch[x][1] = f ;
f = x ;
update(x) ;
}
return -1;
}
void add1(int x ,int y ,int add)
{
access(y) ;
for(int f = 0 ; x ; x = pre[x])
{
splay(x) ;
if(!pre[x])
{
w[x] += add ;
Max[x] += add ;
Min[x] += add ;
Add(f,add) ;
Add(ch[x][1],add) ;
return ;
}
ch[x][1] = f ;
f = x ;
update(x) ;
}
}
void link(int x,int y )
{
make_root(x) ;
pre[x]=y;
}
}lct;
void dfs(int u,int f)
{
for(int i = head[u]; i != -1; i=next1[i])
{
int v = to[i] ;
if(v==f) continue ;
dfs(v,u);
lct.pre[v] = u;
}
}
int next_int() {
char ch;
int res;
bool neg;
while (ch = getchar(), !isdigit(ch) && ch != ‘-‘)
;
if (ch == ‘-‘) {
neg = true;
res = 0;
} else {
neg = false;
res = ch - ‘0‘;
}
while (ch = getchar(), isdigit(ch))
res = res * 10 + ch - ‘0‘;
return neg ? -res : res;
}
int main()
{
int n,m,i,j,k;
int T,case1=0,u,v,c ;
// freopen("in.txt","r",stdin);
cin >> T ;
while(T--)
{
scanf("%d",&n) ;
lct.init();
for( i = 1 ; i <= n ;i++)
{
lct.w[i] = next_int() ;
// lct.Max[i] = lct.Min[i] = lct.w[i];
}
top=0;
memset(head,-1,sizeof(head)) ;
for( i = 1 ; i < n ;i++)
{
u = next_int();
v = next_int();
Unit(u,v) ;
Unit(v,u) ;
}
dfs(1,-1);
scanf("%d",&m) ;
while(m--)
{
//scanf("%d%d%d",&u,&v,&c) ;
u = next_int();
v = next_int();
c = next_int();
printf("%d\n",lct.find(u,v)) ;
lct.add1(u,v,c) ;
}
}
return 0 ;
}
hdu 5052 Yaoge’s maximum profit
标签:des blog http io os ar java for strong
原文地址:http://www.cnblogs.com/20120125llcai/p/4005688.html