cf#590 D 二维树状数组

久未见 提交于 2020-01-14 01:00:42

题意

给一个10^5之内的字符串(小写字母)时限2s

输入n,有n个操作  (n<10^5)

当操作是1的时候,输入位置x和改变的字母

当操作是2的时候,输入区间l和r,有多少不同的字母

思路

二维树状数组

 1 #include<iostream>
 2 #include<cstdio>
 3 #include<cstring>
 4 #include<queue>
 5 #include<map>
 6 #define lowbit(x) x&(-x)
 7 using namespace std;
 8 const int maxn=1e5+10;
 9 char s[maxn];
10 int l,n,yi,er,san;
11 char c;
12 struct node{
13     int tr[maxn];
14     void inint(){
15         memset(tr,0,sizeof(tr));
16     }
17     void updata(int x,int y){
18         for(int i=x; i<=l; i+=lowbit(i)){
19             tr[i]+=y;
20         }
21     }
22     int geshu(int x,int y){
23         int sum1=0,sum2=0;
24         for(int i=x; i>0; i-=lowbit(i)){
25             sum1+=tr[i];
26         }
27         for(int i=y; i>0; i-=lowbit(i)){
28             sum2+=tr[i];
29         }
30         return sum2-sum1;
31     }
32 } a[27];
33 int main(){
34  
35     while(~scanf("%s",&s)){
36         for(int i=0; i<26; i++){
37             a[i].inint();
38         }
39         l=strlen(s);
40         for(int i=0; i<l; i++){
41             a[s[i]-'a'].updata(i+1,1);
42         }
43         scanf("%d",&n);
44         for(int i=0; i<n; i++){
45             scanf("%d",&yi);
46             if(yi==1){
47                 scanf("%d %c",&er,&c);
48                 er--;
49                 a[s[er]-'a'].updata(er+1,-1);
50                 s[er]=c;
51                 a[s[er]-'a'].updata(er+1,1);
52  
53             }
54             else{
55                 scanf("%d%d",&er,&san);
56                 int ans=0;
57                 er--;
58                 for(int i=0; i<26; i++){
59                     //cout<<i<<" "<<a[i].geshu(er,san)<<endl;
60                     if(a[i].geshu(er,san)){
61                         ans+=1;
62                     }
63                 }
64                 printf("%d\n",ans);
65             }
66         }
67     }
68     return 0;
69 }
View Code
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!