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
| #include <cstdio> #include <cstring> #include <iostream> #include <set> #include <algorithm> using namespace std; #define N 20010 #define M 800010 set <int> col[N]; set <int> :: iterator it; struct xy{int x,y;char ctrl[3];}q[N]; int a[N],san[N],next[N],v[N],pre[N],c[N],L[N],R[N],root[N]; int ls[M],rs[M],sum[M]; int n,m,ne,cnt,tot,numa,numb; char ch; void read(int &x){ while (ch = getchar(),ch < '0' || ch > '9'); x = ch - '0'; while (ch = getchar(),ch >= '0' && ch <= '9') x = x * 10 + ch - '0'; } inline void update(int lson,int rson,int x,int k){ sum[++ tot] = sum[x] + k,ls[tot] = lson,rs[tot] = rson; } inline int change(int x,int l,int r,int y,int k){ if (l == r) {update(0,0,x,k);return tot;} int m = l + r >> 1; if (y <= m) ne = change(ls[x],l,m,y,k),update(ne,rs[x],x,k); else ne = change(rs[x],m + 1,r,y,k),update(ls[x],ne,x,k); return tot; } inline void bitup(int x,int p,int k){ for (;x <= n;x += x & -x) c[x] = change(c[x],1,n + 1,p,k); } int ask(int *a,int numa,int *b,int numb,int k){ int ans = 0,l = 1,r = n + 1,m; while (l < r){ m = l + r >> 1; if (k >= m) { for (int i = 0;i < numa;i ++) a[i] = rs[a[i]]; for (int i = 0;i < numb;i ++) b[i] = rs[b[i]]; l = m + 1; }else{ for (int i = 0;i < numa;i ++) ans -= sum[rs[a[i]]]; for (int i = 0;i < numb;i ++) ans += sum[rs[b[i]]]; for (int i = 0;i < numa;i ++) a[i] = ls[a[i]]; for (int i = 0;i < numb;i ++) b[i] = ls[b[i]]; r = m; } } for (int i = 0;i < numa;i ++) ans -= sum[a[i]]; for (int i = 0;i < numb;i ++) ans += sum[b[i]]; return ans; } int query(int x,int y){ numa = numb = 0; int k = y; L[numa ++] = root[x]; for (;x;x -= x & -x) L[numa ++] = c[x]; R[numb ++] = root[y]; for (;y;y -= y & -y) R[numb ++] = c[y]; return ask(L,numa,R,numb,k); } int main(){ read(n);read(m); for (int i = 1;i <= n;i ++) read(a[i]),san[++ cnt] = a[i]; for (int i = 1;i <= m;i ++){ scanf("%s",q[i].ctrl); read(q[i].x);read(q[i].y); if (q[i].ctrl[0] == 'R') san[++ cnt] = q[i].y; } sort(san + 1,san + 1 + cnt); cnt = unique(san + 1,san + 1 + cnt) - san - 1; for (int i = 1;i <= n;i ++) a[i] = lower_bound(san + 1,san + 1 + cnt,a[i]) - san; for (int i = 1;i <= n;i ++){ next[i] = n + 1; if (!v[a[i]]) v[a[i]] = i; else { next[v[a[i]]] = i; pre[i] = v[a[i]]; v[a[i]] = i; } col[a[i]].insert(i); } for (int i = 1;i <= n;i ++) root[i] = change(root[i - 1],1,n + 1,next[i],1),c[i] = root[0]; for (int i = 1;i <= m;i ++){ if (q[i].ctrl[0] == 'Q') printf("%d\n",query(q[i].x - 1,q[i].y)); else{ int pos = q[i].x,val = lower_bound(san + 1,san + 1 + cnt,q[i].y) - san; if (pre[pos]){ bitup(pre[pos],pos,-1); next[pre[pos]] = next[pos]; bitup(pre[pos],next[pos],1); } if (next[pos] < n + 1) pre[next[pos]] = pre[pos]; bitup(pos,next[pos],-1); col[a[pos]].erase(pos); a[pos] = val; it = col[val].upper_bound(pos); if (*it > pos){ next[pos] = *it; pre[*it] = pos; }else next[pos] = n + 1; bitup(pos,next[pos],1); if (it != col[val].begin()){ it --; bitup(*it,next[*it],-1); next[*it] = pos; pre[pos] = *it; bitup(*it,next[*it],1); }else pre[pos] = 0; col[val].insert(pos); } } return 0; }
|