数据结构问题笔记

本文介绍了数据结构中的并查集、二叉堆及其应用,包括洛谷上的相关题目分析,如程序自动分析、小Z的神奇数列。此外,还探讨了平衡树在送花问题中的应用。最后提到了树链剖分和线段树等数据结构的实战技巧。

并查集

洛谷P1955 程序自动分析

相等具有传递性,考虑用并查集维护。

无法用并查集维护不等式,考虑离线,先处理相等的,再将不相等的作为判定即可。

数据范围很大,考虑离散化。

二叉堆

洛谷P2174 小Z的神奇数列

维护四个堆,分别记为 q q q d q dq dq(小根堆), p p p d p dp dp(大根堆)。

  • 对于最大小值的询问,询问堆顶即可。
  • 对于最大值的最小值次幂询问,快速幂即可。
  • 对于删除操作,把待删除的数加入 d q dq dq d p dp dp,当 q q q d q dq dq 的堆顶相同时,pop 即可,询问操作前需保证 q q q d q dq dq 的堆顶两两不相同, q q q d q dq dq 同理。
  • 对于所有数乘积的询问,维护所有数的乘积,在删除操作时乘上该数的逆元即可

类似做法:维护两个堆即可,对于删除操作,将待删除的数标记一下,当堆顶的数被标记时,pop 即可,但是似乎毒瘤出题人卡 map(数的范围 1 ∼ 1 e 8 1\sim1e8 11e8)。
思路三:待填坑

注:模数不是质数(啊~这~),费马小定理用不上了,要用 e x g c d exgcd exgcd

补:似乎拓展欧几里得理论上也是不行的,因为可能出现 gcd ⁡ ( x , p ) ≠ 1 \gcd(x,p)\not=1 gcd(x,p)=1,即原数和模数不互质,然而数据可能是随机的,待更。

平衡树

洛谷 P2073 送花

弱化版平衡树模板题。

另类做法:建立价格到美丽值的映射,维护两个堆,堆存储价格,对于删除操作,将将待删除的数的价格标记标记一下,当堆顶的数被标记时,pop 即可。

然而可以用 STL 的 set 。

总结:对于在数据结构中储存数据,只储存下标或关键数据(比如说用来排序)即可,节省空间。

树链剖分

洛谷P3384 轻重链剖分 / 树链剖分

子树+路径 查询+修改。

点权树剖。

P4114 Qtree1

边权树剖。

线段树 & 树状数组

P2572 [SCOI2010]序列操作

VOJ 1620 小白上树
P4513 小白逛公园
SP1043 GSS1 - Can you answer these queries I
SP1716 GSS3 - Can you answer these queries III

维护 r e v , c h g rev,chg rev,chg 两个 tag 来进行修改操作,规定优先级 c h g > r e v chg>rev chg>rev

区间反转 r e v = r e v xor ⁡ 1 rev=rev \operatorname{xor} 1 rev=revxor1
区间修改为 1 1 1 r e v = 0 , c h g = 1 rev=0,chg=1 rev=0,chg=1
区间修改为 0 0 0 r e v = 0 , c h g = 0 rev=0,chg=0 rev=0,chg=0

标记下传优先更新 c h g chg chg r e v rev rev

维护 s u m 1 , s u m 0 , p r e 1 , p r e 0 , s u f 1 , s u f 0 , m i x 1 , m i x 0 sum_1,sum_0,pre_1,pre_0,suf_1,suf_0,mix_1,mix_0 sum1,sum0,pre1,pre0,suf1,suf0,mix1,mix0 来支持查询,左右儿子为 l c d , r c d lcd,rcd lcd,rcd,区间长度为 l e n len len

s u m 1 = s u m 1 , l c d + s u m 1 , r c d sum_1=sum_{1,lcd}+sum_{1,rcd} sum1=sum1,lcd+sum1,rcd
s u m 0 = s u m 0 , l c d + s u m 0 , r c d sum_0=sum_{0,lcd}+sum_{0,rcd} sum0=sum0,lcd+sum0,rcd
p r e 1 = max ⁡ { p r e 1 , l c d , ( s u m 1 , l c d + p r e 1 r c d ) [ s u m 1 l c d = l e n l c d ] } pre_1=\max\{pre_{1,lcd},(sum_{1,lcd}+pre1_{rcd})[sum1_{lcd}=len_{lcd}]\} pre1=max{pre1,lcd,(sum1,lcd+pre1rcd)[sum1lcd=lenlcd]}
p r e 0 = max ⁡ { p r e 0 , l c d , ( s u m 0 , l c d + p r e 0 , r c d ) [ s u m 0 , l c d = = l e n l c d ] } pre_0=\max\{pre_{0,lcd},(sum_{0,lcd}+pre_{0,rcd})[sum_{0,lcd=}=len_{lcd}]\} pre0=max{pre0,lcd,(sum0,lcd+pre0,rcd)[sum0,lcd==lenlcd]}
s u f 1 = max ⁡ { s u f 1 , r c d , ( s u f 1 , l c d + s u m 1 , r c d ) [ s u m 1 , r c d = l e n r c d ] } suf_1=\max\{suf_{1,rcd},(suf_{1,lcd}+sum_{1,rcd})[sum_{1,rcd}=len_{rcd}]\} suf1=max{suf1,rcd,(suf1,lcd+sum1,rcd)[sum1,rcd=lenrcd]}
s u f 0 = max ⁡ { s u f 0 , r c d , ( s u f 0 , l c d + s u m 0 , r c d ) [ s u m 0 , r c d = l e n r c d ] } suf_0=\max\{suf_{0,rcd},(suf_{0,lcd}+sum_{0,rcd})[sum_{0,rcd}=len_{rcd}]\} suf0=max{suf0,rcd,(suf0,lcd+sum0,rcd)[sum0,rcd=lenrcd]}
m i x 1 = max ⁡ { m i x 1 , l c d , m i x 1 , r c d , s u f 1 , l c d + p r e 1 , r c d } mix_1=\max\{mix_{1,lcd},mix_{1,rcd},suf_{1,lcd}+pre_{1,rcd}\} mix1=max{mix1,lcd,mix1,rcd,suf1,lcd+pre1,rcd}
m i x 0 = max ⁡ { m i x 0 , l c d , m i x 0 , r c d , s u f 0 , l c d + p r e 0 , r c d } mix_0=\max\{mix_{0,lcd},mix_{0,rcd},suf_{0,lcd}+pre_{0,rcd}\} mix0=max{mix0,lcd,mix0,rcd,suf0,lcd+pre0,rcd}

P4145 上帝造题的七分钟 2 / 花神游历各国

SP2713 GSS4 - Can you answer these queries IV

1 0 18 10^{18} 1018 开方 6 6 6 次向下取整即为 1 1 1,当区间和不为区间长度时暴力遍历开方即可。

维护区间最值 m a x , m i n max,min max,min,区间减标记 s u b sub sub,当 m a x ≠ m i n \sqrt{max}\not=\sqrt{min} max =min 时下传标记即可。

P5142 区间方差

维护区间和,区间平方和(均满足结合律)即可 O ( log ⁡ n ) O(\log n) O(logn) 查询, O ( 1 ) O(1) O(1) 算出方差。

P1438 无聊的数列

维护原数组的差分序列即可。

CF242E XOR on Segment

按位考虑即可。

线段树合并 & Dsu On Tree

P4556 [Vani有约会]雨天的尾巴 /【模板】线段树合并

线段树合并,树上差分。

每个点维护一颗动态开点权值线段树,依次合并到父亲节点即可。

// 将 y 合并到 x 上
void merge(int &x,int &y,int xl,int xr){
		if(!x){x=y;return;}if(!y)return;
		if(xl==xr)cnt[x]+=cnt[y],val[x]=val[y];
		else merge(lcd[x],lcd[y],xl,xm),merge(rcd[x],rcd[y],xm+1,xr),update(x);
}
// 将 x 和 y 合并成 z
int merge(int x,int y,int xl,int xr){
	int z=++ndc;if(!x||!y){z=x+y;return z;}
	if(xl==xr)cnt[z]=cnt[x]+cnt[y],val[z]=val[x]+val[y];
	else lcd[z]=merge(lcd[x],lcd[y],xl,xm),rcd[z]=merge(rcd[x],rcd[y],xm+1,xr),update(z);
}

CF600E Lomsat gelral

线段树合并可做。

树上启发式合并 dsu on tree 可做。、

主席树

P1383 高级打字机

主席树,撤回操作。

P3919 【模板】可持久化线段树 1(可持久化数组)

主席树,历史版本询问修改。

P3834 【模板】可持久化线段树 2

静态区间第 k k k 小。

二维偏序

P5459 [BJOI2016]回转寿司

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值