Title Link: Http://codeforces.com/contest/703/problem/D
Give you the number of N, m query, each query asks you to have an even number of times between R number XOR and how much.
We can pre-preprocess prefixes and xor[i], representing 1~i XOR and. Because of the num^num=0, so xor[r] ^ xor[l-1) is to ask for an odd number of times between the l~r of the digital Xor and.
How to courtship several times, then we can first ask L to R does not repeat the number of Xor (for example, 1 1 2 for 1 ^ 2), and then the XOR above the xor[r] ^ xor[l-1], Chi Chi, the elimination of the answer.
If we don't repeat it, we'll use a tree-like array to handle it. First, the inquiry according to R from small to large order, so that the following offline processing. The map has the nearest position I of the a[i] number, and then inserts the a[i] in the tree-like array i position [] and A[i] before removing the position I ', which ensures that the query does not repeat XOR and optimality.
Specific look at the code, you should be able to read.
1 //#pragma COMMENT (linker, "/stack:102400000, 102400000")2#include <algorithm>3#include <iostream>4#include <cstdlib>5#include <cstring>6#include <cstdio>7#include <vector>8#include <cmath>9#include <ctime>Ten#include <list> One#include <Set> A#include <map> - using namespacestd; -typedefLong LongLL; thetypedef pair <int,int>P; - Const intN = 1e6 +5; - intBit[n], xor[n], a[n], ans[n], N; -Map <int,int> MP;//A[i] recently appeared position + structQuery { - intL, R, id; + BOOL operator< (Constquery& CMP)Const { A returnR <CMP.R; at } - }q[n]; - - voidUpdateintIintval) { - for(; I <= n; i + = (i&-i)) -Bit[i] ^=Val; in } - to intSuminti) { + ints =0; - for(; I >=1; I-= (i&-i)) theS ^=Bit[i]; * returns; $ }Panax Notoginseng - intMain () the { + intm; Ascanf"%d", &n); the for(inti =1; I <= N; ++i) { +scanf"%d", A +i); -Xor[i] = xor[i-1] ^ a[i];//prefix xor $ } $scanf"%d", &m); - for(inti =1; I <= m; ++i) { -scanf"%d%d", &Q[I].L, &Q[I].R); theQ[i].id =i; - }WuyiSort (q +1, q + M +1); the intj =1;//structure subscript for inquiry - for(inti =1; I <= N; ++i) { Wu int&temp = Mp[a[i]];//References - if(temp) {//if it's not the first time, then remove the position that appeared before A[i] About Update (temp, a[i]); $ } -temp =i; -Update (temp, a[i]);//Insert the nearest location - while(J <= m && i = =Q[J].R) { A intL = q[j].l-1, r =Q[J].R; +Ans[q[j].id] = SUM (r) ^ sum (l) ^ Xor[r] ^Xor[l]; the++J; - } $ } the for(inti =1; I <= m; ++i) { theprintf"%d\n", Ans[i]); the } the return 0; -}
View Code
The above is the correct code, the following is the tle.
Previously written by Mo team, the data should be too small.
1#include <iostream>2#include <cstdio>3#include <cstring>4#include <algorithm>5#include <cmath>6#include <map>7 using namespacestd;8 Const intMAXN = 1e6 +5;9 typedef __int64 LL;Ten intA[MAXN], u, ANS[MAXN]; One structque { A intL, R, id; - }Q[MAXN]; -Map <int,int>MP; the - BOOLcmp (que x, que y) { - if(x.l/u = = Y.L/u) - returnX.R <Y.R; + returnx.l/u < Y.L/u; - } + A intMain () at { - intN, M; - while(~SCANF ("%d", &N)) { - for(inti =1; I <= N; i++) { -scanf"%d", A +i); - } inscanf"%d", &m); - for(inti =1; I <= m; i++) { toscanf"%d%d", &Q[I].L, &Q[I].R); +Q[i].id =i; - } theU = (int) sqrt (n1.0); *Sort (q +1, q + M +1, CMP); $ intL =1, R =0, num;Panax Notoginseng inttemp =0; - for(inti =1; I <= m; i++) { the while(R >Q[I].R) { +num =--Mp[a[r]]; A if(num) { theTemp ^=A[r]; + } -r--; $ } $ while(R <Q[I].R) { -r++; -num = + +Mp[a[r]]; the if(Num >1) { -Temp ^=A[r];Wuyi } the } - while(L <Q[I].L) { Wunum =--Mp[a[l]]; - if(num) { AboutTemp ^=A[l]; $ } -l++; - } - while(L > Q[I].L) {//the front is still not counted. Al--; +num = + +Mp[a[l]]; the if(Num >1) { -Temp ^=A[l]; $ } the } theAns[q[i].id] =temp; the } the for(inti =1; I <= m; i++) { -printf"%d\n", Ans[i]); in } the } the return 0; About}
View Code
Codeforces Round #365 (Div. 2) D. Mishka and interesting sum (offline tree array + prefix XOR)