AcWing 1270. 数列区间最大值(RMQ问题)
Posted MangataTS
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了AcWing 1270. 数列区间最大值(RMQ问题)相关的知识,希望对你有一定的参考价值。
题目链接
https://www.acwing.com/problem/content/description/1272/
思路
我们这次需要维护一下区间的最大值,也就是经典的 RMQ
问题,由于没有更新操作,所以只写了 build
和 query
部分,原理都非常简单,相当于是模板了 ,详情请看代码
代码
#include<iostream>
#include<algorithm>
#include<cstdio>
using namespace std;
#define endl "\\n"
#define ll long long
#define INF 0x3f3f3f3f3f3f3f3f
const int N = 2e5+10;
ll a[N];
struct Tnode
ll l,r,sum,lazy,Max;
;
struct SegmentTree
Tnode tree[N<<2];
inline void push_up(ll root)//向上更新
tree[root].Max = max(tree[root<<1].Max , tree[(root<<1) | 1].Max);
void build(ll l,ll r,ll root)//建树
tree[root].l = l;
tree[root].r = r;
if(l == r) tree[root].Max = a[l];
else
ll mid = ((r+l) >> 1);
build(l,mid,root<<1);
build(mid+1,r,(root<<1)+1);
push_up(root);
ll query(ll l,ll r,ll root) //区间查询
if(tree[root].l >= l && tree[root].r <= r) return tree[root].Max;
else
ll mid = tree[root].l + ((tree[root].r-tree[root].l) >> 1);
ll ans = -INF;
if(l <= mid) ans = max(ans,query(l,r,root<<1));//如果我们查询区间的左边界比当前节点的中间点小,那么说明查询区间要往左走
if(r > mid) ans = max(ans,query(l,r,(root<<1) + 1));//如果我们查询的右边界要比当前节点的中间节点大,那么说明查询区间要往右走
return ans;
Tree;
int n,m;
int main()
ios::sync_with_stdio(0);cin.tie(0);cout.tie(0);
cin>>n>>m;
for(int i = 1;i <= n; ++i) cin>>a[i];
Tree.build(1,n,1);
ll l,r;
for(int t = 1;t <= m; ++t)
cin>>l>>r;
cout<<Tree.query(l,r,1)<<endl;
/*
Testcase:
input
10 2
3 2 4 5 6 8 1 2 9 7
1 4
3 8
output:
5
8
*/
以上是关于AcWing 1270. 数列区间最大值(RMQ问题)的主要内容,如果未能解决你的问题,请参考以下文章
HDU - 5289 Assignment (RMQ+二分)