ST算法&&RMQ

ST算法是适用于RMQ问题的一种算法,可以在O( nlog(n) )预处理之后,以O( 1 )的复杂度求解区间 [l,r] 的最值问题,也是采用了倍增思想
详细的思想过程放到了代码注释部分

//ST 求解 RMQ问题 
#include<bits/stdc++.h>
using namespace std;

int arr[100];
int f[100][100];
//f[i][j] 表示以i为起始位置,长度为2^j的数列的最值 
int main()
{
	for(int i=0;i<80;i++)arr[i]=i+1; 
	for(int i=0;i<80;i++){
		f[i][0]=arr[i];
		
		//从任意位置开始,长度为0的数列都是只有自己的数列,所以 f[i][0] = arr[i]; 
	}
	int t=log(20)/log(2);
	//如果不这样写的话,2的n次方可能会因为数字过大,循环超时
	//这样写的原因是因为区间的长度是 2^t ,最长不会超过数组的长度
	for(int j=1;j<=t;j++){
		for(int i=0;i<20;i++){
			f[i][j]=max(f[i][j-1],f[i+(1<<(j-1))][j-1]);
		}
	} 
	int l,r;
	while(cin>>l>>r){//求解 [l,r]闭区间内的最大值 
		int k=1;
		while((1<<k)<=r-l+1){
			k++;
		}
		k--;
		
		//k 是满足从l开始长度为 2^k并且使得 l+2^k-1不超过r的最大的k
		//一旦超出边界,求得的最大值将不再是[l,r]内的,而是[l,最大边界]内的 
		
		cout<<max(f[l][k],f[r-(1<<k)+1][k])<<endl;
		
		//[l,r]内的最值可以将区间[l,r]拆开
		//利用上面求出的 k 稍加推论可以知道 
		// [l,r]内的最值 等同于 max(f[l][k],f[r-(1<<k)+1][k])
		// f[l][k] 是从l开始长度为2^k的最值
		// f[r-(1>>k)+1][k] 是从r开始往前推,长度为2^k的最大值
		// 两个区间的交集 >= 原来的区间[l,r]
		// 所以两个区间的最大值就是原区间的最大值 
	}
	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值