题目大意:

给定一个序列,维护每个数字在[L,R]出现的次数以及交换a[x]和a[x+1]的操作

一开始想的分桶法,感觉复杂度还可以吧,常数有点大,于是死得很惨(65分)

  1 #include<cstdio>
  2 #include<cstdlib>
  3 #include<algorithm>
  4 #include<cstring>
  5 #include<cmath>
  6 #include<map>
  7 #include<set>
  8 #include<queue>
  9 #include<vector>
 10 #define INF 0x7f7f7f7f
 11 #define pii pair<int,int>
 12 #define ll long long
 13 #define SIZE 2505
 14 #define MAXN 300005
 15 using namespace std;
 16 
 17 int read(){
 18     int x=0,f=1;char ch=getchar();
 19     while(ch<'0'||ch>'9'){if('-'==ch)f=-1;ch=getchar();}
 20     while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();}
 21     return x*f;
 22 }
 23 int n,num,len;
 24 struct Bucket{
 25     int L;
 26     int a[SIZE];
 27     vector<int> v;
 28     Bucket(){
 29         L=-1;
 30         memset(a,0,sizeof(a));
 31     }
 32     void add(int x){
 33         a[++L]=x;
 34         vector<int>::iterator P=lower_bound(v.begin(),v.end(),x);
 35         v.insert(P,x);
 36     }
 37 }s[250];
 38 //pos:id->position 
 39 //id:
 40 int main()
 41 {
 42 //    freopen("data.in","r",stdin);
 43 //    freopen("my.out","w",stdout);
 44     n=read();int T=read();
 45     len=pow(1.0*n,0.618);
 46     num=(n-1)/len;
 47     for(int i=0;i<n;i++){
 48         s[i/len].add(read());
 49     }
 50     while(T--){
 51         int p=read();
 52         int numl=0,numr=0,posl=0,posr=0;
 53         if(1==p){
 54             int ans=0;
 55             int l=read(),r=read(),c=read();
 56             l--,r--;
 57             numl=l/len,numr=r/len;
 58             posl=l%len,posr=r%len;
 59             if(numl!=numr){
 60                 for(int i=numl+1;i<numr;i++){
 61                     ans+=upper_bound(s[i].v.begin(),s[i].v.end(),c)-lower_bound(s[i].v.begin(),s[i].v.end(),c);
 62                 }
 63                 for(int i=posl;i<=s[numl].L;i++){
 64                     if(s[numl].a[i]==c){
 65                         ans++;
 66                     }
 67                 }
 68                 for(int i=0;i<=posr;i++){
 69                     if(s[numr].a[i]==c){
 70                         ans++;
 71                     }
 72                 }
 73             }
 74             else{
 75                 for(int i=posl;i<=posr;i++){
 76                     if(s[numl].a[i]==c){
 77                         ans++;
 78                     }
 79                 }
 80             }
 81             printf("%d\n",ans);
 82         }
 83         else{
 84             int l=read()-1,r=l+1;
 85             numl=l/len,numr=r/len;
 86             posl=l%len,posr=r%len;
 87             int lc=s[numl].a[posl],rc=s[numr].a[posr];
 88             if(lc==rc){
 89                 continue;
 90             }
 91             vector<int>::iterator it;
 92             it=lower_bound(s[numl].v.begin(),s[numl].v.end(),lc);
 93             s[numl].v.erase(it);
 94             it=lower_bound(s[numl].v.begin(),s[numl].v.end(),rc);
 95             s[numl].v.insert(it,rc);
 96             it=lower_bound(s[numr].v.begin(),s[numr].v.end(),rc);
 97             s[numr].v.erase(it);
 98             it=lower_bound(s[numr].v.begin(),s[numr].v.end(),lc);
 99             s[numr].v.insert(it,lc);
100             swap(s[numl].a[posl],s[numr].a[posr]);
101 //            for(int i=0;i<=num;i++){
102 //                for(int j=0;j<s[i].v.size();j++){
103 //                    printf("%d ",s[i].v[j]);
104 //                }
105 //                printf("\n");
106 //            }
107 //            printf("\n");
108         }
109     }
110     return 0;
111 }
分桶

相关文章:

  • 2022-12-23
  • 2021-05-06
  • 2022-12-23
  • 2021-08-15
  • 2021-06-22
  • 2021-11-11
  • 2021-06-18
  • 2022-12-23
猜你喜欢
  • 2022-01-22
  • 2021-10-20
  • 2021-11-18
  • 2021-07-21
  • 2021-08-09
  • 2021-09-03
  • 2021-06-09
相关资源
相似解决方案