比赛 |
树形数据结构拔高 |
评测结果 |
AAAAAWAAAA |
题目名称 |
聪聪的世界 |
最终得分 |
90 |
用户昵称 |
flyfree |
运行时间 |
10.009 s |
代码语言 |
C++ |
内存使用 |
59.50 MiB |
提交时间 |
2025-04-17 21:25:48 |
显示代码纯文本
#include<bits/stdc++.h>
using namespace std;
#define ll long long
#define pir pair<ll,ll>
#define ls first
#define rs second
#define mp make_pair
#define mod
#define MAXN 1000010
#define inf 1e18
#define qmod(x) (x>mod?x-mod:x)
inline ll read(){
ll x = 0,f = 1;
char c = getchar();
while(c < '0'||c > '9'){
if(c == '-')f = -1;
c = getchar();
}
while(c >= '0'&&c <= '9'){
x = x*10+c-'0';
c = getchar();
}
return x*f;
}
ll n,m;
ll a[MAXN];
struct node_sgt{
ll l[MAXN * 4],r[MAXN * 4],maxz[MAXN * 4],minz[MAXN * 4],tag[MAXN * 4];
void push_up(ll now){
minz[now] = min(minz[now << 1], minz[now << 1 | 1]);
maxz[now] = max(maxz[now << 1], maxz[now << 1 | 1]);
}
void update(ll now, ll v){
maxz[now] += v;
minz[now] += v;
tag[now] += v;
}
void push_down(ll now){
update(now << 1, tag[now]);
update(now << 1 | 1, tag[now]);
tag[now] = 0;
}
void build(ll lz = 1, ll rz = n, ll now = 1){
// cout << lz << " " << rz << " " << now << endl;
maxz[now] = -inf,minz[now] = inf;
l[now] = lz, r[now] = rz;
if(lz == rz){
maxz[now] = minz[now] = a[lz];
return;
}
ll mid = (lz + rz) >> 1;
build(lz, mid, now << 1);
build(mid + 1, rz, now << 1 | 1);
push_up(now);
}
void add(ll lz, ll rz, ll v, ll now = 1){
if(l[now] >= lz && r[now] <= rz){
update(now, v);
return;
}
push_down(now);
ll mid = (l[now] + r[now]) >> 1;
if(lz <= mid)add(lz, rz, v, now << 1);
if(rz > mid)add(lz, rz, v, now << 1 | 1);
push_up(now);
}
void modify(ll pos, ll v, ll now = 1){
if(l[now] == r[now]){
minz[now] = maxz[now] = v;
tag[now] = 0;
return;
}
push_down(now);
ll mid = (l[now] + r[now]) >> 1;
if(pos <= mid)modify(pos, v, now << 1);
else modify(pos, v, now << 1 | 1);
push_up(now);
}
ll Querylmin(ll lz, ll rz, ll v, ll now = 1){
if(lz > rz)return -1;
if(minz[now] > v)return -1;
if(l[now] == r[now]){
return minz[now];
}
push_down(now);
ll mid = (l[now] + r[now]) >> 1;
if(lz > mid)return Querylmin(lz, rz, v, now << 1 | 1);
else if(rz <= mid)return Querylmin(lz, rz, v, now << 1);
else{
ll resr = Querylmin(lz, rz, v, now << 1 | 1);
if(resr == -1)return Querylmin(lz, rz, v, now << 1);
else return resr;
}
}
ll Querylmax(ll lz, ll rz, ll v, ll now = 1){
if(lz > rz)return -1;
if(maxz[now] < v)return -1;
if(l[now] == r[now]){
return maxz[now];
}
push_down(now);
ll mid = (l[now] + r[now]) >> 1;
if(lz > mid)return Querylmax(lz, rz, v, now << 1 | 1);
else if(rz <= mid)return Querylmax(lz, rz, v, now << 1);
else{
ll resr = Querylmax(lz, rz, v, now << 1 | 1);
if(resr == -1)return Querylmax(lz, rz, v, now << 1);
else return resr;
}
}
ll Queryrmin(ll lz, ll rz, ll v, ll now = 1){
if(lz > rz)return -1;
if(minz[now] > v)return -1;
if(l[now] == r[now]){
return minz[now];
}
push_down(now);
ll mid = (l[now] + r[now]) >> 1;
if(lz > mid)return Queryrmin(lz, rz, v, now << 1 | 1);
else if(rz <= mid)return Queryrmin(lz, rz, v, now << 1);
else{
ll resl = Queryrmin(lz, rz, v, now << 1);
if(resl == -1)return Queryrmin(lz, rz, v, now << 1 | 1);
else return resl;
}
}
ll Queryrmax(ll lz, ll rz, ll v, ll now = 1){
if(lz > rz)return -1;
if(maxz[now] < v)return -1;
if(l[now] == r[now]){
return maxz[now];
}
push_down(now);
ll mid = (l[now] + r[now]) >> 1;
if(lz > mid)return Queryrmax(lz, rz, v, now << 1 | 1);
else if(rz <= mid)return Queryrmax(lz, rz, v, now << 1);
else{
ll resl = Queryrmax(lz, rz, v, now << 1);
if(resl == -1)return Queryrmax(lz, rz, v, now << 1 | 1);
else return resl;
}
}
ll Query(ll pos, ll now = 1){
if(l[now] == r[now])return maxz[now];
push_down(now);
ll mid = (l[now] + r[now]) >> 1;
if(pos <= mid)return Query(pos, now << 1);
else return Query(pos, now << 1 | 1);
}
}sgt;
int main(){
freopen("ccsworld.in", "r", stdin);
freopen("ccsworld.out", "w", stdout);
n = read(),m = read();
for(int i = 1;i <= n; ++i)a[i] = read();
sgt.build();
for(int i = 1; i <= m; ++i){
ll op = read();
if(op == 1){
ll x = read();
ll z = sgt.Query(x);
printf("%lld\n", sgt.Querylmin(1, x - 1, z));
}else if(op == 2){
ll x = read();
ll z = sgt.Query(x);
printf("%lld\n", sgt.Querylmax(1, x - 1, z));
}else if(op == 3){
ll x = read();
ll z = sgt.Query(x);
printf("%lld\n", sgt.Queryrmin(x + 1, n, z));
}else if(op == 4){
ll x = read();
ll z = sgt.Query(x);
printf("%lld\n", sgt.Queryrmax(x + 1, n, z));
}else if(op == 5){
ll x = read(),y = read();
ll valx = sgt.Query(x),valy = sgt.Query(y);
sgt.modify(x, valy);
sgt.modify(y, valx);
}else if(op == 6){
ll x = read(),y = read(),v = read();
sgt.add(x, y, v);
}else{
ll x = read(),y = read(),v = read();
sgt.add(x, y, -v);
}
// cout << i << endl;
}
return 0;
}