#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
#define fst first
#define snd second
#define pb push_back
#define SZ(x) (int)x.size()
#define ALL(x) x.begin(),x.end()
#define forn(i,a,b) for(int i = a; i<b;i++)
#define mset(a,v) memset(a,v,sizeof(a))
#define FIN ios::sync_with_stdio(0); cin.tie(0); cout.tie(0);
using namespace std;
using namespace __gnu_pbds;
typedef long long ll;
template< typename T >
using iset = tree<T,null_type,less<T>,rb_tree_tag,tree_order_statistics_node_update>;
struct Node{
ll res;
ll mpsum;
ll mssum;
ll tsum;
Node(ll x){ tsum=x; res=mpsum=mssum=min(x,(ll)0); }
};
Node merge(Node a , Node b){
Node nd=Node(0);
nd.mpsum=min(a.mpsum,b.mpsum+a.tsum);
nd.mssum=min(b.mssum,a.mssum+b.tsum);
nd.tsum=a.tsum+b.tsum;
nd.res=min(a.res+b.tsum,b.res+a.tsum);
nd.res=min(nd.res,a.mpsum+b.mssum);
return nd;
}
struct STree{
ll n;
vector<Node> st;
STree(ll n):n(n),st(4*n+5,Node(0)){}
void upd(ll k, ll l, ll r, ll p, ll v){
if(l+1==r){ st[k]=Node(v); return; }
ll mid = (l+r)/2;
if(mid>p) upd(2*k,l,mid,p,v);
else upd(2*k+1,mid,r,p,v);
st[k]=merge(st[2*k],st[2*k+1]);
}
Node query(ll k, ll l, ll r, ll L, ll R){
if(l>=R||r<=L) return Node(0);
if(l>=L&&r<=R){ return st[k];}
ll mid = (l+r)/2;
return merge(query(2*k,l,mid,L,R),query(2*k+1,mid,r,L,R));
}
void upd(ll p, ll v){ upd(1,0,n,p,v); }
ll query(ll l, ll r){ return query(1,0,n,l,r).res; }
};
int main(){
ll n; cin>>n;
string s; cin>>s;
vector<ll> v(n,0); forn(i,0,n) v[i]+=(s[i]=='C'?1:-1);
STree st(n); forn(i,0,n) st.upd(i,v[i]);
ll q; cin>>q;
forn(i,0,q){
ll l,r; cin>>l>>r; l--;
cout<<-st.query(l,r)<<'\n';
}
return 0;
}