題意:給一棵樹,兩種操作: add1: 給u-v路徑上所有點加上值k, add2:給u-v路徑上所有邊加上k,初始值都為0,問最後每個點和每條邊的值,輸出。
解法:樹鏈剖分可做,剖出來如果直接用線段樹來區間更新的話會tle,所以要換一種姿勢,有一種樹鏈剖分的經典姿勢就是看做樹狀陣列一樣,每次加值的時候,比如u->v之間加乙個值k,那麼在u處+k,v+1處-k即可,然後掃一遍,每次把當前位置要做的操作做完,此時總共加的值就是當前處的值,掃一遍的時候維護的是字首的和,也就是兩個ans不清零。
這題卡時間太緊,不加讀入掛會t,不加輸出掛的話跑4921ms,也是飄過,加了輸入輸出掛才稍微好點,4687ms,可能是樹鏈剖分不夠優越
**:
#pragma comment(linker, "/stack:102400000,102400000")#includeview code#include
#include
#include
#include
#include
#define lll __int64
using
namespace
std;
#define n 100007
int siz[n]; //
子樹大小
int son[n]; //
重兒子int dep[n]; //
深度int pos[n],apos[n]; //
int top[n]; //
所在重鏈的祖先
int fa[n]; //
父節點lll eans[n],nans[n]; //
答案int head[2*n],tot,pos,n,m;
struct
edge
g[2*n],qe[10*n],qn[10*n];
int heade[10*n],headn[10*n],tote,totn;
struct
node
edge[n];
void
init()
void addedge(int u,int
v)void addnedge(int u,int v) //
代替vector來存操作
void addeedge(int u,int v) //
代替vector來存操作
void dfs(int u,intf)}
void dfs2(int u,int
top)
}void addedge(int u,int v,int
k) addeedge(pos[fx],k);
addeedge(pos[u]+1,-k);
u =fa[fx];
fx =top[u];
}if(dep[u] >dep[v]) swap(u,v);
addeedge(pos[son[u]],k);
addeedge(pos[v]+1,-k);
}void addnode(int u,int v,int
k) addnedge(pos[fx],k);
addnedge(pos[u]+1,-k);
u =fa[fx];
fx =top[u];
}if(dep[u] >dep[v]) swap(u,v);
addnedge(pos[u],k);
addnedge(pos[v]+1,-k);
}inline
intin
()
returna;}
inline
void
out(lll num)
int ans[22],top=0
;
while(num!=0
)
if(top==0
) putchar('0
');for(int i=top-1;i>=0;i--)
}int
main()
dep[
0] = 0
; dfs(
1,0);
dfs2(
1,1);
while(m--)
printf(
"case #%d:\n
",cs++);
lll ansedge = 0,ansnode = 0
;
for(i=1;i<=n;i++)
for(i=1;i<=n;i++)
for(i=1;i)
if(n == 1) puts(""); //
pe..
}
return0;
}
HDU 5044 Tree (樹鏈剖分)
這題用線段樹貌似過不了,和nyoj 的士兵殺敵五一樣,經過樹鏈剖分後,就把樹剖分成許多鏈,這樣可以對整個鏈操作,結合字首和的思想,如果某個節點到祖先節點更新這間的所有節點,可以把祖先節點 k 讓當前節點編號 1 減 k 這樣最後跑一邊陣列就可以了,葉子節點的時候類似。pragma comment l...
HDU5044 Tree 樹鏈剖分
大致題意 add1 u v u到v路徑上所有點的權值加上k,add2 u 到v路徑上所有邊的權值加上k 最後輸出所有點的權值,邊的權值。樹鏈剖分預處理然後來個線性o n 的操作。剛開始用線段樹tle了.1 pragma comment linker,stack 1024000000,10240000...
poj3237 Tree 樹鏈剖分
這個題是spoj的改版 是在原來的題意上增加了區間取反操作 所以只需要在spoj375的基礎上再線段樹上增加乙個取反標誌 同時在維護乙個區間最小值 因為在區間取反了以後 區間的最大值就是區間原來的最小值 嗯 就這樣就可以了 include include include using namespac...