fhq_treap 求助
查看原帖
fhq_treap 求助
324412
Filberte楼主2024/4/2 16:13

样例过了,但是交上去0分,求调

#include <bits/stdc++.h>
#define file(x) freopen(x ".in","r",stdin);freopen(x ".out","w",stdout)
#define fp(...) fprintf(stderr,__VA_ARGS__)
#define de(x) cerr << #x << ":" << x << endl;
using namespace std;
bool _mst;
int n, q;string s;
mt19937 gen(random_device{}());
int rnd(){return gen();}
const int N = 1e5 + 100;
int idx;
int val[N], dat[N], ls[N], rs[N], siz[N], pmn[N], pmx[N], smn[N], smx[N], sum[N];
int cov[N], rev[N], inv[N];//cover, reverse, invert
int rt;
void Cov(int u, int num){
    val[u] = num;
    if(num == 1){
        pmn[u] = smn[u] = 0;
        sum[u] = pmx[u] = smx[u] = siz[u];
    }
    else{
        sum[u] = pmn[u] = smn[u] = -siz[u];
        pmx[u] = smx[u] = 0; 
    }
    cov[u] = num, rev[u] = 0, inv[u] = 0;
}
void Rev(int u){
    swap(ls[u], rs[u]);
    swap(pmn[u], smn[u]);
    swap(pmx[u], smx[u]);
    rev[u] ^= 1;
}
void Inv(int u){ 
    swap(pmn[u], pmx[u]);
    pmn[u] = -pmn[u], pmx[u] = -pmx[u];
    swap(smn[u], smx[u]);
    smn[u] = -smn[u], smx[u] = -smx[u];
    inv[u] ^= 1;
    val[u] = -val[u];
    cov[u] = -cov[u];
}
void push_down(int u){  
    if(cov[u]){
        if(ls[u]) Cov(ls[u], cov[u]);
        if(rs[u]) Cov(rs[u], cov[u]);
        cov[u] = 0;
    }
    if(inv[u]){
        if(ls[u]) Inv(ls[u]);
        if(rs[u]) Inv(rs[u]);
        inv[u] = 0;
    }
    if(rev[u]){
        if(ls[u]) Rev(ls[u]);
        if(rs[u]) Rev(rs[u]);
        rev[u] = 0;
    }
}
void push_up(int u){
    siz[u] = siz[ls[u]] + siz[rs[u]] + 1;
    pmn[u] = min(pmn[ls[u]], sum[ls[u]] + val[u] + pmn[rs[u]]);
    pmx[u] = max(pmx[ls[u]], sum[ls[u]] + val[u] + pmx[rs[u]]);
    smn[u] = min(smn[rs[u]], sum[rs[u]] + val[u] + smn[ls[u]]);
    smx[u] = max(smx[rs[u]], sum[rs[u]] + val[u] + smx[ls[u]]); 
    sum[u] = sum[ls[u]] + val[u] + sum[rs[u]];
}
pair<int, int> split(int u, int k){ // 1 ~ k || k + 1 ~ siz
    if(!u) return make_pair(0, 0);
    push_down(u);
    if(siz[ls[u]] >= k){
        auto [x, y] = split(ls[u], k);
        ls[u] = y;
        push_up(u);
        return make_pair(x, u);
    }
    else{
        auto [x, y] = split(rs[u], k - siz[ls[u]] - 1);
        rs[u] = x;
        push_up(u);
        return make_pair(u, y);
    }
}
int merge(int x, int y){
    if(!x || !y) return x | y;  
    if(dat[x] < dat[y]){
        push_down(x);
        rs[x] = merge(rs[x], y);
        push_up(x);
        return x;
    }
    else{
        push_down(y);
        ls[y] = merge(x, ls[y]);
        push_up(y);
        return y;
    }
}
int New(int v){
    int u = ++idx;
    val[u] = sum[u] = v;
    dat[u] = rnd();
    siz[u] = 1;
    pmn[u] = smn[u] = min(0, v);
    pmx[u] = smx[u] = max(0, v);
    ls[u] = rs[u] = 0;
    return u;
}
void ins(int k){rt = merge(rt, New(k));}
void Rep(int l, int r, int num){
    auto[p, z] = split(rt, r);
    auto[x, y] = split(p, l - 1);
    Cov(y, num);
    rt = merge(merge(x, y), z);
}
void rever(int l, int r){
    auto[p, z] = split(rt, r);
    auto[x, y] = split(p, l - 1);
    Rev(y);
    rt = merge(merge(x, y), z);
}
void invert(int l, int r){
    auto[p, z] = split(rt, r);
    auto[x, y] = split(p, l - 1);
    Inv(y);
    rt = merge(merge(x, y), z);
}
int qry(int l, int r){
    auto[p, z] = split(rt, r);
    auto[x, y] = split(p, l - 1);
    int res = max(0, (-pmn[y] + 1) / 2) + max(0, (smx[y] + 1) / 2);
    rt = merge(merge(x, y), z);
    return res;
}
bool _med;
int main(){
    ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
    auto _tb = std::chrono::high_resolution_clock::now();
    cin >> n >> q >> s;
    for(int i = 0;i < n;i++){
        int x = (s[i - 1] == '(') ? 1 : -1;
        ins(x);
    }
    while(q--){
        int l, r;
        cin >> s >> l >> r;
        if(s[0] == 'R'){
            cin >> s;
            if(s[0] == '(') Rep(l, r, 1);
            else Rep(l, r, -1);
        }
        else if(s[0] == 'S'){
            rever(l, r);
        }
        else if(s[0] == 'I'){
            invert(l, r);   
        }
        else{
            cout << qry(l, r) << '\n';
        }
    }
    auto _te = std::chrono::high_resolution_clock::now();
    auto elapsed = std::chrono::duration_cast<std::chrono::nanoseconds>(_te - _tb);
    cerr <<  elapsed.count() * 1e-9 << " seconds.\n";
    cerr << 1.0 * (&_mst - &_med) / 1024.0 / 1024.0 << "MB\n";
    return 0;
}
2024/4/2 16:13
加载中...