您的位置:首页 > 理论基础 > 数据结构算法

关于线段树的作用与其他数据结构的替代

2017-08-25 09:12 211 查看
众所周知,sgt十分难写 并且如果模板记错 调试难度也十分大,然而今天我在写树剖的时候突发奇想,我们是否可以用一些数据结构代替线段树?以下是我的一些总结:

1.区间修改单点查询

这个十分简单 基本的查分用树状数组维护就好了

代码实现:略

2.区间修改区间查询

2相比1提高了许多难度,不过2个树状数组依旧是可以解决的,第一个树状树状为S1 第二个为S2,S1维护基本的查分,S2维护di*i 原理如下

显然有如下公式:

ai=∑xi=1

然后得:

∑xi=1ai=∑xi=1∑ij=1di

继续推得:

∑xi=1ai=∑xi=1∗(x−i+1)di

最后化简一下就发现2个数组啦:

∑xi=1ai=∑xi=1(x+1)∗di−∑xi=1di∗i

代码如下啦啦啦:


void add(int x,int y)
{for(int i=x;i<=n;i+=lb(i)) c1[i]+=y,c2[i]+=(long long)x*y;}
long long sum(int x)
{
long long ans(0);
for(int i=x;i;i-=lb(i)) ans+=(x+1)*c1[i]-c2[i];
return ans;
}


我有恶意压行嫌疑 但显然不长不是喵!

3.区间最大最小值

哈!一道RMQ好题!我一般是用ST表写 这里直接上代码吧

for(int j=1;(1<<j)<=n;j++)
for(int i=1;i<=n+1-(1<<j);i++)
f[i][j]=max(f[i][j-1],f[i+(1<<(j-1))][j-1]);


k=int(log2(r-l+1));
printf("%d\n",max(f[l][k],f[r-(1<<k)+1][k]));


十分简洁啧啧啧 然后我们的线段树就如此被替代了?不然。。。RMQ只能离线。。。。。。。。。。。。。。。。

4.区间乘法!

显然将∑换成∏就ok了 但是如果乘加交替的话,貌似比较难维护,博主正在辛勤研究ing~~ 好了最后谢谢大家!
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: