ST算法(倍增)

ST算法是一种高效的数据结构,用于解决区间最值查询问题。通过预处理,可在O(NlogN)时间内构建数据结构,并在O(1)时间内回答任意区间的最大值或最小值。本文详细介绍了ST算法的工作原理,包括初始化、查询过程以及代码实现。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

作用:

ST算法是用来对任意一个数组,求其任以(l~r)区间内的最大值(最小值也可以)。

题解:

引出:

首先遇到这一类题,我们可以暴力查找,但是这种方法如果询问多次,直接让您原地起飞,显然我们机智的"前人"是不能忍的,于是牛逼的ST算法出现了。
其方法主要是以O(NlogN)O(N log_{} N)O(NlogN)的时间,最后以O(1)O(1)O(1)时间回答。

题解:

设f[i][j]表示子区间(i,i+2j−1)(i,i + 2^{j} - 1)i,i+2j1中的最大值。我们可以倍增区间长度,那么则有f[i][j]=max(f[i][j−1],f[i+(1<<(j−1))][j−1])f[i][j] = max(f[i][j - 1], f[i + (1<<(j - 1))][j-1])f[i][j]=max(f[i][j1],f[i+(1<<(j1))][j1]),即是(i——i+2j−1)(i——i + 2^{j} - 1)ii+2j1区间最大值=将长度为2j2^{j}2j分成两半:(i——i+2j−1)(i——i+2^{j - 1})ii+2j1(i+2j−1(i+2^{j - 1}(i+2j1——iii + 2j2^{j}2j - 1)中间取最大。可以想成递推的方式吧。

初始化:
f[i][0]即是指iii~iii最大值=a[i];

输出:
假设我们需要查询区间[l,r]中的最小值,令k=log2(r−l+1)k=log2(r−l+1)k=log2(rl+1),则最小值为max(f[l][k],f[r−(1<<k)+1][k])max(f[l][k], f[r - (1 << k) + 1][k])max(f[l][k],f[r(1<<k)+1][k])
证明:
更据前面分析我们知道,两个数组表示(l,l+2k−1)(l, l + 2^{k} - 1)l,l+2k1(r−2k+1,r)(r - 2^{k} + 1, r)r2k+1,r所以我们只需要证明这两个区间覆盖了l——rl —— rlr及证r−2k+1<=l+2k−1r - 2^{k} + 1 <= l + 2^{k} - 1r2k+1<=l+2k1,这里用移项然后再带入k最后的到r−l>=0r-l>=0rl>=0,及原式成立。

代码:

#include <iostream>
#include <cstdio>
#include <cmath>
#include <algorithm>
using namespace std; 
const int MAXN = 1e6 + 5;

int n, m, x, y, a[MAXN], f[MAXN][105];
void ST(int n) {
	for(int i = 1;i <= n; i++) {
		f[i][0] = a[i];
	}
	int t = log(n) / log(2) + 1;
	for(int j = 1;j < t; j++) {
		for(int i = 1; i <= n - (1 << j) + 1; i++) {
			f[i][j] = max(f[i][j - 1], f[i + (1<<(j-1))][j - 1]);
		}
	} 
} 

int STF(int l, int r) {
	int k = log(r - l + 1) / log(2);
	return max(f[l][k], f[r - (1 << k) + 1][k]);
}
int main() {
	scanf("%d %d", &n, &m);
	for(int i = 1;i <= n; i++) {
		scanf("%d", &a[i]);
	}
	ST(n);
	for(int i = 1;i <= m; i++) {
		scanf("%d %d", &x, &y);
		printf("%d\n", STF(x, y));
	}
	return 0;
}
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值