1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160
|
#include <bits/stdc++.h> #define all(vec) vec.begin(),vec.end() #define CLR(i,a) memset(i,a,sizeof(i)) #define fi first #define se second #define pb push_back #define SZ(a) ((int) a.size()) #define FOR(i, a, b) for (int i = (a); i <= (b); ++i) #define ROF(i, a, b) for (int i = (a); i >= (b); --i) #define getFro(vec) (vec.empty()?0:vec.front()) #define getBac(vec) (vec.empty()?0:vec.back()) #define debug(var) cerr << #var <<":"<<var<<"\n"; #define DEBUG(variable) do { std::cerr << #variable << ":"; for (const auto& elem : variable) { std::cerr << elem << " ";}std::cerr << "\n";} while (0) #define uniVec(var) do { sort(var.begin(),var.end());var.resize(unique(var.begin(),var.end())-var.begin());} while (0) #define debugN(var,N) do{ std::cerr<<#var<<":"; FOR(i,1,N){ std::cerr<<var[i]<<" "; } std::cerr<<"\n"; }while(0) #define debugMap(variable) do { std::cerr << #variable << ":\n"; for (const auto& pair : variable) { std::cerr << " " << pair.first << " => " << pair.second << "\n"; } std::cerr << std::endl; } while (0) #define lson(var) (var<<1) #define rson(var) ((var<<1)+1) #define vecMxx(vec,x) (vec.end()-lower_bound(all(vec),x)) // vec中大于x的数有几个
using namespace std;
typedef long long ll;typedef unsigned long long ull; typedef double DB;typedef long double LD; typedef __int128 i128;typedef pair<DB,DB> pdd;typedef pair<ll,bool> plb; typedef pair<ll,ll> pll; typedef array<ll,3> arr3;typedef array<ll,2> arr2; constexpr ll MAXN=static_cast<ll>(1e6)+10,INF=static_cast<ll>(1e18)+3; constexpr ll mod=static_cast<ll>(1e9)+7; constexpr double eps=1e-8;
ll N,M,Q,X,K,lT,A[MAXN]; /*
*/ // namespace F=FHQ; 使用的时候简化可以这样 namespace FHQ{ // fhq-treap 使用namespace可以即起到打包,又避免实例化 const int maxn=static_cast<ll>(1.1e6)+10; using KEY=int; KEY key[maxn]; int pri[maxn],ls[maxn],rs[maxn],size[maxn]; int root=0,cnt=0; // 超int范围问题不大,反正是正的负的也无所谓,他也不报错反正 mt19937 rng(chrono::steady_clock::now().time_since_epoch().count()); inline void makeN(KEY val){++cnt;pri[cnt]=rng();key[cnt]=val;ls[cnt]=0;rs[cnt]=0; size[cnt]=1;} // pushup 相当于有清空和向上传递两层意义 inline void pushup(int node){size[node]=size[ls[node]]+size[rs[node]]+1;} //把树 node 按值 val 分裂成两颗子树:左边的 x 和 右边的 y。 void split(int node,KEY val,int &x,int &y){ if(!node) {x=0,y=0;return;} if(key[node]<=val){ x=node; // 左树,包括他自己,全部<=val(因为左树符合条件,不需要重新选一个了) split(rs[node],val,rs[node],y); // 右树还要继续分 }else{ // key[node]>val,说明右树(包括他自己)全部大于val y=node; // x其实是从更上面传下来的rs[node],其实是想找一个比<=val的右树 split(ls[node],val,x,ls[node]); } pushup(node); } // 按pri合并,pri小的在上面 int merge(int x,int y){ if(!x || !y) return x+y; if(pri[x]<pri[y]){ // 那么x是左树,左子树自然是不用动的 rs[x]=merge(rs[x],y); // 这个顺序其实是为了不会破坏BST性质,因为rs[x]<=y(key) pushup(x); return x; }else{ // y是右树,右子树自然不用动 ls[y]=merge(x,ls[y]); pushup(y); return y; } } inline void insert(KEY val){ int x,y; // 将树按值分裂为两个子树 split(root,val,x,y); makeN(val); // 新建节点cnt root=merge(x,cnt); root=merge(root,y); } inline void del(KEY val){ int x,y,z; split(root,val,x,y); split(x,val-1,x,z); z=merge(ls[z],rs[z]); root=merge(x,z); root=merge(root,y); } inline int getrank(KEY val){ int x,y; // 因为分裂出来一颗树<=val-1,另外一颗树<val split(root,val-1,x,y); int ret=size[x]+1; root=merge(x,y); return ret; } KEY _kth(int node,int rank){ if(size[ls[node]]>=rank){ return _kth(ls[node],rank); }else{ if(size[ls[node]]+1>=rank) return key[node]; else return _kth(rs[node],rank-size[ls[node]]-1); } } inline KEY kth(int rank){ return _kth(root,rank); } inline KEY prex(KEY val){return kth(getrank(val)-1);} inline KEY sufx(KEY val){return kth(getrank(val+1));} }
inline void solve(){ scanf("%lld%lld",&N,&M); namespace F=FHQ; FOR(_,1,N){ int x; scanf("%d",&x);F::insert(x); } int up=0,ans=0; FOR(_,1,M){ int op,x; scanf("%d%d",&op,&x); x^=up; if(op==1){F::insert(x);} else if(op==2){F::del(x);} else if(op==3){up=FHQ::getrank(x);ans^=up;} else if(op==4){up=F::kth(x);ans^=up;} else if(op==5){up=F::prex(x);ans^=up;} else if(op==6){up=F::sufx(x);ans^=up;} } printf("%d\n",ans); }
int main() { // ios::sync_with_stdio(false); // cin.tie(0);cout.tie(0); // scanf("%lld",&lT); // while(lT--){ // solve(); // } solve(); return 0; } /* AC https://www.luogu.com.cn/record/219062740 */
|