emmm,存26个字母的位子,然后用树状数组维护即可的水题...分块(= - =应该可以写,我以后会认真学分块的).
代码如下:

#include <bits/stdc++.h>
using namespace std;
const int N=1e5+5,M=27;
char s[N];
int n;
int bit[M][N];
int lowbit(int x) { return x&(-x); }
void insert(int pos,int val,int ch)
{
    while(pos<=n)
    {
        bit[ch][pos]+=val;
        pos+=lowbit(pos);
    }
}

int query(int pos,int ch)
{
    int res=0;
    while(pos>0)
    {
        res+=bit[ch][pos];
        pos-=lowbit(pos);
    }
    return res;
}

int main()
{
    int q;
    scanf("%s",s+1);n=strlen(s+1);
    for(int i=1;i<=n;i++)
    {
        insert(i,1,s[i]-'a');
    }
    scanf("%d",&q);
    //1单点修改,2区间查询.
    while(q--)
    {
        int f;
        scanf("%d",&f);
        if(f==1)//单点修改.
        {
            int x;char y;
            scanf("%d",&x);cin>>y;
            insert(x,-1,s[x]-'a');
            insert(x,1,y-'a');
            s[x]=y;
        }
        else//区间查询.
        {
            int x,y,ans=0;
            scanf("%d%d",&x,&y);
            for(int i=0;i<26;i++)
            {
                if(query(y,i)-query(x-1,i)) ans++;
            }
            printf("%d\n",ans);
        }
    }
    return 0;
}