求调 只过了样例和Subtask #1
查看原帖
求调 只过了样例和Subtask #1
936388
Suin_tryin楼主2025/8/1 13:08
#include<iostream>
using namespace std;
int n, m;
int a[100010];
struct node {
    bool is0, is1;
    int sum0, sum1, lsum0, lsum1, rsum0, rsum1, cnt0, cnt1;
    //sum0/1区间最长连续0/1
    //lsum0/1 rsum0/1区间前/后缀0/1个数
    //cnt0/1 区间0/1总数
}tr[400010];
int tag0[400010], tag1[400010], tag2[400010]; //tag0/1区间赋值0/1,tag2区间取反
void pushup(int u) {
    tr[u].cnt0 = tr[u << 1].cnt0 + tr[u << 1 | 1].cnt0;
    tr[u].cnt1 = tr[u << 1].cnt1 + tr[u << 1 | 1].cnt1;
    tr[u].is0 = tr[u << 1].is0 & tr[u << 1 | 1].is0;
    tr[u].is1 = tr[u << 1].is1 & tr[u << 1 | 1].is1;
    tr[u].lsum0 = tr[u << 1].lsum0;
    if(tr[u << 1].is0) tr[u].lsum0 = tr[u << 1].cnt0 + tr[u << 1 | 1].lsum0;
    tr[u].lsum1 = tr[u << 1].lsum1;
    if(tr[u << 1].is1) tr[u].lsum1 = tr[u << 1].cnt1 + tr[u << 1 | 1].lsum1;
    tr[u].rsum0 = tr[u << 1 | 1].rsum0;
    if(tr[u << 1 | 1].is0) tr[u].rsum0 = tr[u << 1 | 1].cnt0 + tr[u << 1].rsum0;
    tr[u].rsum1 = tr[u << 1 | 1].rsum1;
    if(tr[u << 1 | 1].is1) tr[u].rsum1 = tr[u << 1 | 1].cnt1 + tr[u << 1].rsum1;
    tr[u].sum0 = max(max(tr[u << 1].sum0, tr[u << 1 | 1].sum0), tr[u << 1].rsum0 + tr[u << 1 | 1].lsum0);
    tr[u].sum1 = max(max(tr[u << 1].sum1, tr[u << 1 | 1].sum1), tr[u << 1].rsum1 + tr[u << 1 | 1].lsum1);
}
void build(int u, int l, int r) {
    if(l == r) {
        if(a[l]) tr[u].is1 = tr[u].sum1 = tr[u].lsum1 = tr[u].rsum1 = tr[u].cnt1 = 1;
        else tr[u].is0 = tr[u].sum0 = tr[u].lsum0 = tr[u].rsum0 = tr[u].cnt0 = 1;
        return ;
    }
    int mid = l + r >> 1;
    build(u << 1, l , mid);
    build(u << 1 | 1, mid + 1, r);
    pushup(u);
}
void pushdown(int u, int l, int r) {
    int mid = l + r >> 1;
    if(tag0[u]) {
        tag0[u << 1] = 1; tag1[u << 1] = 0; tag2[u << 1] = 0;
        tr[u << 1].is0 = 1, tr[u << 1].is1 = 0;
        tr[u << 1].sum0 = tr[u << 1].lsum0 = tr[u << 1].rsum0 = tr[u << 1].cnt0 = mid - l + 1;
        tr[u << 1].sum1 = tr[u << 1].lsum1 = tr[u << 1].rsum1 = tr[u << 1].cnt1 = 0;
        tag0[u << 1 | 1] = 1; tag1[u << 1 | 1] = 0; tag2[u << 1 | 1] = 0;
        tr[u << 1 | 1].is0 = 1, tr[u << 1 | 1].is1 = 0;
        tr[u << 1 | 1].sum0 = tr[u << 1 | 1].lsum0 = tr[u << 1 | 1].rsum0 = tr[u << 1 | 1].cnt0 = r - mid;
        tr[u << 1 | 1].sum1 = tr[u << 1 | 1].lsum1 = tr[u << 1 | 1].rsum1 = tr[u << 1 | 1].cnt1 = 0;
        tag0[u] = 0;
    }
    if(tag1[u]) {
        tag1[u << 1] = 1; tag0[u << 1] = 0; tag2[u << 1] = 0;
        tr[u << 1].is1 = 1, tr[u << 1].is0 = 0;
        tr[u << 1].sum1 = tr[u << 1].lsum1 = tr[u << 1].rsum1 = tr[u << 1].cnt1 = mid - l + 1;
        tr[u << 1].sum0 = tr[u << 1].lsum0 = tr[u << 1].rsum0 = tr[u << 1].cnt0 = 0;
        tag1[u << 1 | 1] = 1; tag0[u << 1 | 1] = 0; tag2[u << 1 | 1] = 0;
        tr[u << 1 | 1].is1 = 1, tr[u << 1 | 1].is0 = 0;
        tr[u << 1 | 1].sum1 = tr[u << 1 | 1].lsum1 = tr[u << 1 | 1].rsum1 = tr[u << 1 | 1].cnt1 = r - mid;
        tr[u << 1 | 1].sum0 = tr[u << 1 | 1].lsum0 = tr[u << 1 | 1].rsum0 = tr[u << 1 | 1].cnt0 = 0;
        tag1[u] = 0;
    }
    if(tag2[u]) {
        swap(tr[u << 1].sum0, tr[u << 1].sum1);
        swap(tr[u << 1].lsum0, tr[u << 1].lsum1);
        swap(tr[u << 1].rsum0, tr[u << 1].rsum1);
        swap(tr[u << 1].cnt0, tr[u << 1].cnt1);
        swap(tr[u << 1].is0, tr[u << 1].is1);
        if(tag0[u << 1]) tag0[u << 1] = 0, tag1[u << 1] = 1;
        else if(tag1[u << 1]) tag1[u << 1] = 0, tag0[u << 1] = 1;
        else tag2[u << 1] ^= 1;
        
        swap(tr[u << 1 | 1].sum0, tr[u << 1 | 1].sum1);
        swap(tr[u << 1 | 1].lsum0, tr[u << 1 | 1].lsum1);
        swap(tr[u << 1 | 1].rsum0, tr[u << 1 | 1].rsum1);
        swap(tr[u << 1 | 1].cnt0, tr[u << 1 | 1].cnt1);
        swap(tr[u << 1 | 1].is0, tr[u << 1 | 1].is1);
        if(tag0[u << 1 | 1]) tag0[u << 1 | 1] = 0, tag1[u << 1 | 1] = 1;
        else if(tag1[u << 1 | 1]) tag1[u << 1 | 1] = 0, tag0[u << 1 | 1] = 1;
        else tag2[u << 1] ^= 1;
        tag2[u] = 0;
    }
}
void change0(int u, int l, int r, int x, int y) {
    if(x <= l && r <= y) {
        tag0[u] = 1; tag1[u] = 0; tag2[u] = 0;
        tr[u].is0 = 1, tr[u].is1 = 0;
        tr[u].sum0 = tr[u].lsum0 = tr[u].rsum0 = tr[u].cnt0 = r - l + 1;
        tr[u].sum1 = tr[u].lsum1 = tr[u].rsum1 = tr[u].cnt1 = 0;
        return;
    }
    pushdown(u, l, r);
    int mid = l + r >> 1;
    if(x <= mid) change0(u << 1, l, mid, x, y);
    if(y > mid) change0(u << 1 | 1, mid + 1, r, x, y);
    pushup(u);
}
void change1(int u, int l, int r, int x, int y) {
    if(x <= l && r <= y) {
        tag1[u] = 1; tag0[u] = 0; tag2[u] = 0;
        tr[u].is1 = 1, tr[u].is0 = 0;
        tr[u].sum1 = tr[u].lsum1 = tr[u].rsum1 = tr[u].cnt1 = r - l + 1;
        tr[u].sum0 = tr[u].lsum0 = tr[u].rsum0 = tr[u].cnt0 = 0;
        return;
    }
    pushdown(u, l, r);
    int mid = l + r >> 1;
    if(x <= mid) change1(u << 1, l, mid, x, y);
    if(y > mid) change1(u << 1 | 1, mid + 1, r, x, y);
    pushup(u);
}
void change2(int u, int l, int r, int x, int y) { 
    if(x <= l && r <= y) {
        swap(tr[u].sum0, tr[u].sum1);
        swap(tr[u].lsum0, tr[u].lsum1);
        swap(tr[u].rsum0, tr[u].rsum1);
        swap(tr[u].cnt0, tr[u].cnt1);
        swap(tr[u].is0, tr[u].is1);
        if(tag0[u]) tag0[u] = 0, tag1[u] = 1;
        else if(tag1[u]) tag1[u] = 0, tag0[u] = 1;
        else tag2[u] ^= 1;
        return ;
    }
    pushdown(u, l, r);
    int mid = l + r >> 1;
    if(x <= mid) change2(u << 1, l, mid, x, y);
    if(y > mid) change2(u << 1 | 1, mid + 1, r, x, y);
    pushup(u);
}
int query1(int u, int l, int r, int x, int y) {
    if(x <= l && r <= y) return tr[u].cnt1;
    pushdown(u, l, r);
    int mid = l + r >> 1;
    int ans = 0;
    if(x <= mid) ans += query1(u << 1, l, mid, x, y);
    if(y > mid) ans += query1(u << 1 | 1, mid + 1, r, x, y);
    return ans;
}
node query2(int u, int l, int r, int x, int y) {
    if(x <= l && r <= y) return tr[u];
    pushdown(u, l, r);
    int mid = l + r >> 1;
    if(y <= mid) return query2(u << 1, l, mid, x, y);
    else if(x > mid) return query2(u << 1 | 1, mid + 1, r, x, y);
    else {
        node xx;
        node ll = query2(u << 1, l, mid, x, mid), rr = query2(u << 1 | 1, mid + 1, r, mid + 1, y);
        xx.cnt1 = ll.cnt1 + rr.cnt1;
        xx.cnt0 = ll.cnt0 + rr.cnt0;
        xx.is0 = ll.is0 & rr.is0;
        xx.is1 = ll.is1 & rr.is1;
        xx.lsum0 = ll.lsum0;
        if(ll.is0) xx.lsum0 = ll.cnt0 + rr.lsum0;
        xx.lsum1 = ll.lsum1;
        if(ll.is1) xx.lsum1 = ll.cnt1 + rr.lsum1;
        xx.rsum0 = rr.rsum0;
        if(rr.is0) xx.rsum0 = rr.cnt0 + ll.rsum0;
        xx.rsum1 = rr.rsum1;
        if(rr.is1) xx.rsum1 = rr.cnt1 + ll.rsum1;
        xx.sum0 = max(max(ll.sum0, rr.sum0), ll.rsum0 + rr.lsum0);
        xx.sum1 = max(max(ll.sum1, rr.sum1), ll.rsum1 + rr.lsum1);
        return xx;
    }
}
int main() {
    ios::sync_with_stdio(false);
    cin.tie(0); cout.tie(0);
    cin >> n >> m;
    for(int i = 1; i <= n; i ++) cin >> a[i];
    build(1, 1, n);
    for(int i = 1; i <= m; i ++) {
        int op, l, r; cin >> op >> l >> r;
        l ++, r ++;
        if(op == 0) change0(1, 1, n, l, r);
        if(op == 1) change1(1, 1, n, l, r);
        if(op == 2) change2(1, 1, n, l, r);
        if(op == 3) cout << query1(1, 1, n, l, r) << endl;
        if(op == 4) cout << query2(1, 1, n, l, r).sum1 << endl;
        //cout << i << endl;
    }
    return 0;
}
2025/8/1 13:08
加载中...