C++ ST表

最近反正学得很杂,做到什么发现还不会就写写吧。(我也不知道我为什么现在还不会ST表)

初始化就是倍增,以前一直不知道怎么查询,一看博客发现世界真奇妙,原来可以通过两个重合了一部分的区间来查询,,,,,,,,,


f [ i ] [ j ] f[i][j] f[i][j]表示 i i i开始的长度为 2 j 2^j 2j的区间的最大(小)值,先初始化 f [ i ] [ 0 ] = a i f[i][0]=a_i f[i][0]=ai,递推式 f [ i ] [ j ] = max ⁡ {   f [ i + 2 j − 1 ] [ j − 1 ] , f [ i ] [ j − 1 ]   } f[i][j]=\max\{\ f[i+2^{j-1}][j-1],f[i][j-1]\ \} f[i][j]=max{ f[i+2j1][j1],f[i][j1] },这个和倍增求LCA差不多。

要求 [ l , r ] [l,r] [l,r]的最大值,可以这样:
求最值图示
k = ⌊ log ⁡ 2 ( r − l + 1 ) ⌋ k=\left\lfloor\log_2\left(r-l+1\right)\right\rfloor k=log2(rl+1),则 [ l , r ] [l,r] [l,r]的最大值是 max ⁡ {   f [ l ] [ k ] , f [ r − 2 k + 1 ] [ k ]   } \max\{\ f[l][k],f[r-2^k+1][k]\ \} max{ f[l][k],f[r2k+1][k] }
但是我也不知道为什么求 ⌊ log ⁡ 2 ( r − l + 1 ) ⌋ \left\lfloor\log_2\left(r-l+1\right)\right\rfloor log2(rl+1) 2 k 2^k 2k1<<k)是 O ( 1 ) O(1) O(1)的(难道不是 O ( log ⁡ ) O(\log) O(log)的吗)。


log ⁡ \log log存下来可以优化一些。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值