#include <bits/stdc++.h>
#define mid (b+e)/2
#define left node<<1
#define right (node<<1)|1
#define mx 100005
using namespace std;

#include <ext/pb_ds/assoc_container.hpp>
#include <ext/pb_ds/tree_policy.hpp>
using namespace __gnu_pbds;
#define ordered_set tree<int, null_type,less<int>, rb_tree_tag,tree_order_statistics_node_update>
#define ordered_multiset tree<pair<int, int>, null_type,less<pair<int, int> >, rb_tree_tag,tree_order_statistics_node_update>

int arr[mx];
ordered_multiset t[4*mx];
void init(int node, int b, int e)
{
    if(b==e)
    {
        t[node].insert({arr[b], b});
        return;
    }
    init(left,b,mid);
    init(right,mid+1,e);
    for(auto x:t[left]) t[node].insert(x);
    for(auto x:t[right]) t[node].insert(x);
}

int query(int node, int b, int e, int i, int j, int x)
{
    // cout<<node<<":"<<b<<":"<<e<<":"<<i<<":"<<j<<"\n";
    if(b>j || e<i) return 0;
    if(i<=b && j>=e){
        // cout<<"===>\n";
        // for(auto [xx, yy]:t[node]) cout<<xx<<":"<<yy<<" "; cout<<"))";
        int ret = t[node].order_of_key({x+1, 0});
        // cout<<node<<":"<<ret<<")";
        return ret;
    }
    return query(left, b, mid, i, j, x) + query(right, mid+1, e, i, j, x);
}

void update(int node, int b, int e, int i, int x){
    t[node].erase(t[node].find({arr[i], i}));
    t[node].insert({x, i});
    if(b==e) return;
    if(i<=mid) update(left, b, mid, i, x);
    else update(right, mid+1, e, i, x);
}

int main()
{
    ios_base::sync_with_stdio(false);cin.tie(NULL);
    int n, q;
    cin>>n>>q;
    for(int i=1; i<=n; i++) cin>>arr[i];
    init(1, 1, n);

    while(q--){
        char c;
        cin>>c;
        if(c=='C'){
            int l, r, x;
            cin>>l>>r>>x;
            cout<<query(1, 1, n, l, r, x)<<"\n";
        } else {
            int i, x;
            cin>>i>>x;
            update(1, 1, n, i, x);
            arr[i]=x;
        }
    }
}