RMQ

RMQ问题:在给定的一个长度位N的区间中,有M个询问,每次询问给出区间[L,R],求出区间段元素的

最大值/最小值。对于RMQ问题很容易想到遍历的做法,将区间[L,R]中的元素遍历一遍,即可寻找到

最大/最小值,但当区间长度较大,询问次数较多,就会耗费大量的时间。RMQ问题可以用线段树和ST

表两种做法,下面介绍ST表。

ST表法:

ST表是用来解决RMQ问题非常高效的方法,通过O(nlong)的预处理之后,可以在O(1)时间

内找到所要的答案。其中预处理就是用到了动态规划的思想。

定义F(i,j)表示以i为下标的元素为起点,区间长度为2^j的区间最值 此时区间范围是[i,i+2j-1-1]

预处理:容易发现初始状态为 F(i,0),此时该值表示区间[i,i]的最值,F(i,0)=ai;

状态转移:可以将[i,j]分成长度为2j-1的两段,一段为[i,i+2j-1-1],另一端为[i+2j−1,i+2j-1]则

F(i,j)=max{f(i,j-1),f(i+2j-1,j-1)}

代码:

void ST(int n)
{
    for(int i=1;i<=n;i++)                            //预处理
        dp[i][0]=i;            
        
    for(int j=1;(1<<j)<=n;j++)
        for(int i=1;i+(1<<j)-1<=n;i++)
        {
            int a=dp[i][j-1];int b=dp[i+(1<<(j-1))][j-1];
            dp[i][j]=a<b?a:b;
        }    
}
View Code

相关文章: