小知識:異或xor 滿足結合律、交換律。另外a xor a=0,也就是說a xor b xor c=e,那麼b xor c = e xor a,也就是說可以字首和。
做法一:樹鏈剖分,線段樹維護。複雜度o(nlog^2n
)(注意坑點:因為權值在邊上,所以交界處的值不能算進去)
做法二:樹上字首和,用s[x]表示根節點到x的路徑上的權值異或值,那麼兩個點上路徑的異或值就是s[a] xor s[b]。複雜度o(n+m)
做法三:lct,把邊化成點,然後瞎搞。**老是tle....我也沒辦法啊,畢竟常數大,暫且先這樣吧
//樹鏈剖分
#include #include #define maxn 200010
using namespace std;
int n, m, head[maxn], next[maxn], to[maxn], tmp[maxn], val[maxn], w[maxn], fa[maxn],
size[maxn], son[maxn], tot, tim, deep[maxn], tid[maxn], top[maxn];
struct segtree
}*root;
void adde(int a, int b, int v)
void build(segtree *p, int l, int r)
build(p->lch=new segtree,l,mid);
build(p->rch=new segtree,mid+1,r);
p->w=p->lch->w xor p->rch->w;
}int segsum(segtree *p, int l, int r)
void dfs1(int pos)
}void dfs2(int pos, int tp)
}int sum(int a, int b)
int main()
void input()
nd[maxn], *s[maxn];
inline int read(int x=0)
inline int getwh(node *x)
inline bool isroot(node *x)
inline void join(node *x, node *y, int wh)
inline void rever(node *x)
inline void pushdown(node *x)
}inline void pushup(node *x)
inline void rotate(node *x)
inline void splay(node *x)
if(getwh(x)^getwh(y))rotate(x);else rotate(y);
rotate(x); }}
inline void access(node *x)
}inline void makeroot(node *x)
inline void link(node *x, node *y)
void init()
}inline int work(int a, int b)
int main()
Luogu2420 讓我們異或吧
題目描述 異或是一種神奇的運算,大部分人把它總結成不進製加法.在生活中 xor運算也很常見。比如,對於乙個問題的回答,是為1,否為0.那麼 a是否是男生 xor b是否是男生 a和b是否能夠成為情侶 好了,現在我們來製造和處理一些複雜的情況。比如我們將給出一顆樹,它很高興自己有n個結點。樹的每條邊上...
luogu2420 讓我們異或吧
這題就沒人用並查集嗎,我弱弱地問一句 然而是先並,後查的 建立乙個帶權並查集 g x 表示節點x到他直接父親的異或值 根據異或的可亂搞的性質 注意並查集一定要先getf一下 然後合併同根據異或可亂搞的性質 rt所示 mspaint真心毒瘤 查詢的時候先getf一下 然後直接g u g v 即可 in...
洛谷 2420 讓我們異或吧
題目描述 異或是一種神奇的運算,大部分人把它總結成不進製加法.在生活中 xor運算也很常見。比如,對於乙個問題的回答,是為1,否為0.那麼 a是否是男生 xor b是否是男生 a和b是否能夠成為情侶 好了,現在我們來製造和處理一些複雜的情況。比如我們將給出一顆樹,它很高興自己有n個結點。樹的每條邊上...