将(i, a[i])当作点,对a[i]这个维度扫描,在i这个维度上面建立扫描线
#include<bits/stdc++.h>
using namespace std;
const int N = 2e5+10;
array<int, 4> que[N];
array<int, 2> a[N];
// 线段树维护树链剖剖分的dfs序
struct Node{
int l, r;
int minn;
}tr[4*N];
void pushup(Node &F, Node L, Node R){
F.minn = min(L.minn, R.minn);
}
void pushup(int u){
pushup(tr[u], tr[u << 1], tr[u << 1 | 1]);
}
void build(int u, int l, int r){
if(l == r){
// 这里注意要加个id,获得序列上l位置的点的是那个点,然后获得他的权值
tr[u] = {l, r, 0x3f3f3f3f};
}
else{
tr[u] = {l, r, 0x3f3f3f3f};
int mid = l + r >> 1;
build(u<<1, l, mid), build(u<<1|1, mid+1, r);
pushup(u);
}
}
void modify(int u, int x, int v){
if(tr[u].l >= x && tr[u].r <= x) {
tr[u].minn = v;
}
else{
int mid = tr[u].l + tr[u].r >> 1;
if(x <= mid) modify(u<<1, x, v);
else if(x > mid) modify(u<<1|1, x, v);
pushup(u);
}
}
Node query(int u, int l, int r){
if(tr[u].l >= l && tr[u].r <= r) return tr[u];
else{
int mid = tr[u].l + tr[u].r >> 1;
if(l > mid) return query(u<<1|1, l, r);
else if(r <= mid) return query(u<<1, l, r);
else{
Node res;
Node L = query(u << 1, l, r), R = query(u << 1 | 1, l, r);
pushup(res, L, R);
return res;
}
}
}
int res[N];
int main(){
int n, m; cin >> n >> m;
memset(res, 0x3f, sizeof res);
for(int i = 1; i <= n; i ++){
int x; scanf("%d", &x);
a[i] = {x, i};
}
for(int i = 1; i <= m; i ++){
int l, r, x; scanf("%d %d %d", &l, &r, &x);
que[i] = {x, l, r, i};
}
sort(a + 1, a + 1 + n);
reverse(a + 1, a + 1 + n);
sort(que + 1, que + 1 + m);
reverse(que + 1, que + 1 + m);
build(1, 1, n);
int i, j;
for(i = 1, j = 1; i <= m + 1; i ++){
while(j <= n && que[j][0] > a[i][0]){
res[que[j][3]] = query(1, que[j][1], que[j][2]).minn;
j ++;
}
if(i == m + 1) break;
modify(1, a[i][1], a[i][0]);
}
for(int i = 1; i <= m; i ++){
if(res[i] != 0x3f3f3f3f) printf("%d\n", res[i]);
else printf("-1\n");
}
}
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。