GukiZ and GukiZiana
64-bit integer IO format: %I64d Java class name: (Any)
Professor GukiZ was playing with arrays again and accidentally discovered new function, which he called GukiZiana. For given array a, indexed with integers from 1 to n, and numbery, GukiZiana(a, y) represents maximum value of j - i, such that aj = ai = y. If there is no y as an element in a, then GukiZiana(a, y) is equal to - 1. GukiZ also prepared a problem for you. This time, you have two types of queries:
- First type has form 1 l r x and asks you to increase values of all ai such that l ≤ i ≤ r by the non-negative integer x.
- Second type has form 2 y and asks you to find value of GukiZiana(a, y).
For each query of type 2, print the answer and make GukiZ happy!
Input
The first line contains two integers n, q (1 ≤ n ≤ 5 * 105, 1 ≤ q ≤ 5 * 104), size of array a, and the number of queries.
The second line contains n integers a1, a2, ... an (1 ≤ ai ≤ 109), forming an array a.
Each of next q lines contain either four or two numbers, as described in statement:
If line starts with 1, then the query looks like 1 l r x (1 ≤ l ≤ r ≤ n, 0 ≤ x ≤ 109), first type query.
If line starts with 2, then th query looks like 2 y (1 ≤ y ≤ 109), second type query.
Output
For each query of type 2, print the value of GukiZiana(a, y), for y value for that query.
Sample Input
4 3
1 2 3 4
1 1 2 1
1 1 1 1
2 3
2
2 3
1 2
1 2 2 1
2 3
2 4
0
-1
Source
1 #include <bits/stdc++.h> 2 using namespace std; 3 typedef long long LL; 4 const int maxn = 1010; 5 LL a[maxn*maxn],lazy[maxn],x; 6 vector<int>block[maxn]; 7 int b_size,N,pos[maxn*maxn],n,q,cmd,L,R; 8 bool cmp(const int x,const int y) { 9 if(a[x] == a[y]) return x < y; 10 return a[x] < a[y]; 11 } 12 void update(int L,int R,LL x) { 13 int k = pos[L],t = pos[R]; 14 if(k == t) { 15 for(int i = L; i <= R; ++i) a[i] += x; 16 sort(block[k].begin(),block[k].end(),cmp); 17 return; 18 } 19 for(int i = k + (pos[L-1] == k); i <= t - (pos[R + 1] == t); ++i) lazy[i] += x; 20 if(pos[L-1] == k) { 21 for(int i = L; pos[i] == k; ++i) a[i] += x; 22 sort(block[k].begin(),block[k].end(),cmp); 23 } 24 if(pos[R+1] == t) { 25 for(int i = R; pos[i] == t; --i) a[i] += x; 26 sort(block[t].begin(),block[t].end(),cmp); 27 } 28 } 29 LL query(LL x) { 30 int L = -1,R = -1,i; 31 for(i = 1; i <= N; ++i){ 32 a[0] = x - lazy[i]; 33 vector<int>::iterator it = lower_bound(block[i].begin(),block[i].end(),0,cmp); 34 if(it == block[i].end()) continue; 35 if(a[*it] + lazy[i] == x){ 36 L = *it; 37 break; 38 } 39 } 40 if(L == -1) return -1; 41 for(int j = N; j >= i; --j){ 42 a[n+1] = x - lazy[j]; 43 vector<int>::iterator it = lower_bound(block[j].begin(),block[j].end(),n+1,cmp); 44 if(it == block[j].begin()) continue; 45 --it; 46 if(a[*it] + lazy[j] == x){ 47 R = *it; 48 break; 49 } 50 } 51 return R - L; 52 } 53 int main() { 54 ios::sync_with_stdio(false); 55 cin.tie(0); 56 cin>>n>>q; 57 b_size = ceil(sqrt(n*1.0)); 58 for(int i = 1; i <= n; ++i) { 59 cin>>a[i]; 60 pos[i] = (i - 1)/b_size + 1; 61 block[pos[i]].push_back(i); 62 } 63 N = (n - 1)/b_size + 1; 64 for(int i = 1; i <= N; ++i) sort(block[i].begin(),block[i].end(),cmp); 65 while(q--) { 66 cin>>cmd; 67 if(cmd == 1) { 68 cin>>L>>R>>x; 69 update(L,R,x); 70 } else { 71 cin>>x; 72 cout<<query(x)<<endl; 73 } 74 } 75 return 0; 76 }