90分求调,hack倒数第二个
查看原帖
90分求调,hack倒数第二个
1198913
封禁用户楼主2025/7/30 18:37
#include <iostream>
#include <algorithm>
#include <cstring>
#include <vector>
using namespace std;
typedef long long LL;

const int N = (3e5 + 10) * 60;
LL n, m, trie[N][2], idx;
LL fa[N], ssize[N], st[N];

void del(LL u){
    int t = __lg(u), p = 0;
    //自顶向下建树
    for (int i = t; i >= 0; i--){
        int v = u >> i, lowb = v & 1;
        if (trie[p][lowb] == 0){
            trie[p][lowb] = ++idx;
            ssize[idx] = ((LL)1 << n - __lg(v)) - 1;
            fa[idx] = p;
        }
        p = trie[p][lowb];
    }
    if (st[p]) return;
    if (fa[p] != 0) st[p] = 1;
    int q = p;
    p = fa[p];
    // 自底向上更新大小
    while(p != 0){
        ssize[p] -= ssize[q];
        if (!st[p])
            p = fa[p];
        else break;
    }
}

LL get(LL u){
    int t = __lg(u), p = 0;
    for (int i = t; i >= 0; i--){
        int v = u >> i, lowb = v & 1;
        if (trie[p][lowb] == 0){
            trie[p][lowb] = ++idx;
            ssize[idx] = ((LL)1 << n - __lg(v)) - 1;
            fa[idx] = p;
        }
        p = trie[p][lowb];
    }
    while(fa[p] != 0 && !st[p]) p = fa[p];
    return ssize[p];
}

int main(){
    ios::sync_with_stdio(false);cin.tie(nullptr);cout.tie(nullptr);
    cin >> n >> m;
    
    LL res = 0;
    while(m--){
        LL op, u; cin >> op >> u;
        if (op == 1) del(u);
        else res ^= get(u);
    }
    cout << res;
    
    return 0;
}

2025/7/30 18:37
加载中...