如題,已知一棵包含n個結點的樹(連通且無環),每個節點上包含一 個數值, 需要支援以下操作 :
操作1 :格式: 1 x y z表示將樹從x到y結點最短路徑上所有節點的值都加上z
操作2 :格式: 2 x y表示求樹從x到y結點最短路徑上所有節點的值之和
操作3:格式: 3 x z表示將以為根節點的子樹內所有節點值都加上z
操作4:格式: 4 x表示求以x為根節點的子樹內所有節點值之和
做國家集訓隊的題的時候發現打炸了
感覺自己樹剖有點問題
所以又跑過去刷刷樹剖
這麼簡單的東西就不寫多了
**:
#include#define n 200005
#define ll long long
#define mid ((l+r)>>1)
#define len (r-l+1)
using namespace std;
int n,m,root,mod,u,v,w,opt,x,y,z;
int a[n];
struct edge
edge[n<<1];
int cnt=0,head[n];
inline void add_edge(int from,int to)
templateinline void read(t &res)
/*樹鏈剖分的兩個dfs*/
int dep[n],fa[n],size[n],son[n];
void dfs1(int u,int f)
pushdown(rt,l,r);
modify(rt<<1,l,mid,x,y,v);
modify(rt<<1|1,mid+1,r,x,y,v);
pushup(rt);
}int query(int rt,int l,int r,int x,int y)//求和
void build(int rt,int l,int r)//建樹
build(rt<<1,l,mid);
build(rt<<1|1,mid+1,r);
pushup(rt);
}/*主體部分*/
void modify_edge(int x,int y,int v)//鏈修改
int ask_edge(int x,int y)//鏈查詢
void modify_tree(int rt,int v)//樹修改
int ask_tree(int rt)//樹查詢
void init()
int main()
init();
for(register int i=1;i<=m;++i)
else if(opt==2)//鏈查詢最小值
else if(opt==3)//樹增加
else if(opt==4)//樹求和
}return 0;}/*
5 5 2 24
7 3 7 8 0
1 21 5
3 14 1
3 4 2
3 2 2
4 51 5 1 3
2 1 3
*/
樹鏈剖分 P3384 模板 樹鏈剖分
題目描述 戳這裡 題解 其實樹剖的重點就在於輕重鏈,這篇文章寫的很好 然而我線段樹寫得全是問題,改了半天2333 如下 include include include using namespace std const int maxn 100005 int n,m,root,tt,tot,lnk ...
luogu3384 樹鏈剖分
辣雞題目毀我青春!以前寫線段樹,指標從來不賦初值,偏偏這道題乖張,本來應該1a的題目我提交了29遍!我的ac率,我的時間!呃,吐槽完了。還是自己習慣不好 輕重邊剖分之後每個點的tid其實就是它的dfs序。tid陣列順著輸出其實就是樹的先序遍歷 允許我亂用概念吧 那麼以乙個節點為根節點的子樹就是剛進d...
樹鏈剖分 洛谷 P3384 模板 樹鏈剖分
step1 problem 題目 給你一棵n個點樹,m個操作,r是根,結果取模mod.操作1 格式 1 x y z 表示將樹從x到y結點最短路徑上所有節點的值都加上z 操作2 格式 2 x y 表示求樹從x到y結點最短路徑上所有節點的值之和 操作3 格式 3 x z 表示將以x為根節點的子樹內所有節...