【概述】

     RMQ(Range Minimum/Maximum Query),即区间最值查询,是指这样一个问题:对于长度为n的数列A,回答若干询问RMQ(A,i,j)(i,j<=n),返回数列A中下标在i,j之间的最小/大值。

一般解决这类区间问题可以用线段树来做,比较通用。但是线段树的代码量有点多。这里介绍另一种算法,ST(Sparse Table)算法。

ST(Sparse Table)算法是一个非常有名的在线处理RMQ问题的算法,它可以在O(nlogn)时间内进行预处理,然后在O(1)时间内回答每个查询。

【构建】  
      该算法是基于倍增思想设计的在线算法,之所以称之为倍增,是因为算法记录从每个元素开始的连续的长度为2k的区间中元素的最值。
      类似于动态规划,F[i, j]表示从第i个数起连续2j个数中 ( 区间为[i,i+2j-1] )的最值。状态转移方程F[i, j]=max/min(F[i,j-1], F[i + 2j-1,j-1]),转移时需要注意别让超界了。
      这个状态转移方程不难想到,一张图就能说明:
【查询】

对于一个查询区间 [i,j] ,只要找到一个或者多个2的整数倍长度的区间覆盖[i,j] ,取这些区间最值的最值就是答案了。

如何把[i,j]覆盖完整?一种办法是把区间的长度按照二进制分成多个2的整数倍区间,显然这些区间是不重叠的,这样求多次最值就能得到答案。不过这种发放增加了算法常数,一次查询可能就要求几十次最值。

还有种更好的方法,原理是:为了减少分割出的区间数量,允许区间重叠,这样所有的情况下最多只要两个区间就好了,见下图:

   只要求出k就好了,k=(int)((log(j-i+1.0)/log(2.0)))。

【代码】

以下代码基于数组下表从0开始。

初始化:

 //n为元数的个数
//bitn为n的二进制位数,取下整(int)(log(n)/log(2))
for (int i=; i<n; ++i)
f[i][]=input[i];
for (int j=; j<bitn; ++j)
for (int i=; i<n; ++i)
{
if (i+(<<(j-))>=n) break;
f[i][j]=max(f[i][j-],f[i+(<<(j-))][j-]);
}

查询:

 int query(int s,int e)  //查询区间[s,e]的最值
{
int k=(int)((log(e-s+1.0)/log(2.0)));
return max(f[s][k],f[e-(<<k)+][k]);
}

RMQ ---- ST(Sparse Table)算法的更多相关文章

  1. RMQ(ST(Sparse Table))(转载)

    1. 概述 RMQ(Range Minimum/Maximum Query),即区间最值查询,是指这样一个问题:对于长度为n的数列A,回答若干询问RMQ(A,i,j)(i,j<=n),返回数列A ...

  2. ST (Sparse Table:稀疏表)算法

    1541:[例 1]数列区间最大值 时间限制: 1000 ms         内存限制: 524288 KB提交数: 600     通过数: 207 [题目描述] 输入一串数字,给你 MM 个询问 ...

  3. 稀疏表(ST / Sparse Table)

    RMQ问题: 给定一个序列,每次询问一个区间最小值 / 最大值. 没有修改. //拿区间最大值来举例. memset(ans, -INF, sizeof(ans)); for (int i = 1; ...

  4. codeforce 359D 二分+ 动态规划(sparse table)

    原题链接:http://codeforces.com/problemset/problem/359/D 思路:首先对符合题目的长度(r-l)从0到n-1进行二分查找,对每一个长度进行check,看是否 ...

  5. POJ 3264 Balanced Lineup RMQ ST算法

    题意:有n头牛,编号从1到n,每头牛的身高已知.现有q次询问,每次询问给出a,b两个数.要求给出编号在a与b之间牛身高的最大值与最小值之差. 思路:标准的RMQ问题. RMQ问题是求给定区间内的最值问 ...

  6. RMQ—ST表

    RMQ(Range Minimum/Maximum Query),RMQ是一个求给定范围内最大最小值的问题.我们一般使用st算法来解决这类问题(Sparse Table).这个算法原理不难,主要是各种 ...

  7. 一维二维Sparse Table

    写在前面: 记录了个人的学习过程,同时方便复习 Sparse Table 有些情况,需要反复读取某个指定范围内的值而不需要修改 逐个判断区间内的每个值显然太浪费时间 我们希望用空间换取时间 ST表就是 ...

  8. poj 3264 区间最大最小值 RMQ问题之Sparse_Table算法

    Balanced Lineup Time Limit: 5000 MS Memory Limit: 0 KB 64-bit integer IO format: %I64d , %I64u Java ...

  9. hdu 3183 A Magic Lamp RMQ ST 坐标最小值

    hdu 3183 A Magic Lamp RMQ ST 坐标最小值 题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3183 题目大意: 从给定的串中挑 ...

随机推荐

  1. centos 7 安装codeblocks

    CentOS7安装Code::Blocks 在CentOS7上安装Codelocks的过程. 1.安装gcc,需要c和c++两部分,默认安装下,CentOS不安装编译器的,在终端输入以下命令即可yum ...

  2. win10 ubuntu16双系统安装教程

    一. 知识准备 1.材料 前提: 本文档是在win10 64位下进行安装的!32位的安装注意其中的一些细节即可 硬件: X86_64 位电脑 硬盘有 40G 空闲 软件:[百度搜索即可] (1) Ul ...

  3. hnust 原石法阵

    问题 F: 原石法阵 时间限制: 1 Sec  内存限制: 128 MB提交: 1098  解决: 161[提交][状态][讨论版] 题目描述 WZH有一个由原石构成的n阶三角形魔法阵,三角形魔法阵如 ...

  4. Nginx下配置codeigniter框架

    原来在winserver+Apache环境下工作良好的一个微信公众号后台迁移到阿里云(环境:Ubuntu 64位 | PHP5.4 | Nginx1.6)下却频出 404,403,只能访问CI rou ...

  5. CodeBlocks X64 SVN 编译版

    CodeBlocks X64 SVN 编译版 采用官方最新的SVN源码编译而来,纯64位的,所以32位系统是不能使用的.字体使用的是微软的YaHei UI字体,如果有更好的字节建议,可以留言. 由于直 ...

  6. Day4 自定义控件/ListView/RecyclerView

    创建自定义控件 引入布局 在新增的title.xml中创建一个自定义的标题栏: <LinearLayout xmlns:android="http://schemas.android. ...

  7. 聊聊、Mybatis XML

    引入相应的依赖包 <dependency><groupId>org.mybatis</groupId><artifactId>mybatis-sprin ...

  8. composer 库无法提交git

    composer require firebase/php-jwt 安装了该库,想提交到版本库,无论如何也提交不上去,.ignore中也没忽略,网上寻找答案,说有个.git文件夹需要删除 PHPSTO ...

  9. 【bzoj5055】膜法师 离散化+树状数组

    题目描述 给定一个序列$a$,求满足$i<j<k$且$a_i<a_j<a_k$的三元组$(i,j,k)$的个数. 输入 第一行1个数 n 第二行n个数 a_i 输出 一个数,表 ...

  10. 【bzoj3747】[POI2015]Kinoman 线段树区间合并

    题目描述 一个长度为n的序列,每个数为1~m之一.求一段连续子序列,使得其中之出现过一次的数对应的价值之和最大. 输入 第一行两个整数n,m(1<=m<=n<=1000000). 第 ...