Advertisement
istinishat

Mo's Algo/Sqrt Decomposition

Aug 29th, 2017
284
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. /*
  2. theory from here:
  3. https://blog.anudeep2011.com/mos-algorithm/
  4. */
  5. // soluton of problem : http://lightoj.com/volume_showproblem.php?problem=1188  
  6. #include<bits/stdc++.h>
  7. using namespace std;
  8.  
  9. #define si(n) scanf("%d",&n)
  10. #define f first
  11. #define s second
  12. #define mp(a,b) make_pair(a,b)
  13. #define MAX 100005
  14.  
  15. vector<pair<int,int> >quary,original;
  16. int arr[MAX],cnt[MAX];
  17. int n,t,q,block;
  18. map<pair<int,int>,int>mm;
  19.  
  20. bool compare(pair<int,int>x, pair<int,int>y)
  21. {
  22.     // Different blocks, sort by block.
  23.     if (x.f/block != y.f/block)
  24.         return x.f/block < y.f/block;
  25.  
  26.     // Same block, sort by R value
  27.     return x.s < y.s;
  28. }
  29.  
  30. int main()
  31. {
  32.     //freopen("input.txt","r",stdin);
  33.     int i,j,k;
  34.     si(t);
  35.     for(int cs=1;cs<=t;cs++){
  36.         mm.clear();
  37.         quary.clear();
  38.         original.clear();
  39.         //memset(arr,0,sizeof(arr));
  40.         memset(cnt,0,sizeof(cnt));
  41.         si(n);si(q);
  42.         for(i=1;i<=n;i++)
  43.             si(arr[i]);
  44.         for(i=1;i<=q;i++){
  45.             int l,r;
  46.             si(l);si(r);
  47.             quary.push_back(mp(l,r));
  48.             original.push_back(mp(l,r));
  49.         }
  50.         block=sqrt(n);
  51.         sort(quary.begin(),quary.end(),compare);
  52.         int curr_l=1,curr_r=1,ans=1;
  53.         cnt[arr[1]]++;
  54.         for(i=0;i<quary.size();i++){
  55.             int l=quary[i].f,r=quary[i].s;
  56.             while(curr_l<l){
  57.                 cnt[arr[curr_l]]--;
  58.                 if(!cnt[arr[curr_l]])ans--;
  59.                 curr_l++;
  60.             }
  61.             while(curr_l>l){
  62.                 curr_l--;
  63.                 cnt[arr[curr_l]]++;
  64.                 if(cnt[arr[curr_l]]==1)ans++;
  65.             }
  66.  
  67.             while(curr_r<r){
  68.                //cout<<curr_r<<endl;
  69.                 curr_r++;
  70.                 cnt[arr[curr_r]]++;
  71.                 if(cnt[arr[curr_r]]==1)ans++;
  72.             }
  73.             while(curr_r>r){
  74.                 cnt[arr[curr_r]]--;
  75.                 if(!cnt[arr[curr_r]])ans--;
  76.                 curr_r--;
  77.             }
  78.             //cout<<l<<' '<<r<<' '<<curr_l<<' '<<curr_r<<endl;
  79.             mm[mp(l,r)]=ans;
  80.         }
  81.         printf("Case %d:\n",cs);
  82.         for(i=0;i<original.size();i++){
  83.             printf("%d\n",mm[mp(original[i].f,original[i].s)]);
  84.         }
  85.     }
  86.     return 0;
  87. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement