#include <bits/stdc++.h>
using namespace std;
const string bases = "AGTC";
const int Maxb = 4;
const int Maxn = 70005;
struct item {
int prior, myval, val[Maxb], cnt;
int l, r;
item(int myval = 0): prior(rand()), cnt(1), myval(myval), l(0), r(0) {
fill(val, val + Maxb, 0);
val[myval]++;
}
};
char tmp[Maxn];
int tlen;
vector <item> T;
int n;
int my[Maxn];
int q;
int A[Maxb], B[Maxb];
void createNew(int val = 0) { T.push_back(item(val)); }
int getLst() { return int(T.size()) - 1; }
int cnt (int it) {
return it ? T[it].cnt: 0;
}
void upd_cnt (int it) {
if (it) {
T[it].cnt = cnt(T[it].l) + cnt(T[it].r) + 1;
for (int i = 0; i < Maxb; i++)
T[it].val[i] = (T[it].l? T[T[it].l].val[i]: 0) +
(T[it].r? T[T[it].r].val[i]: 0);
T[it].val[T[it].myval]++;
}
}
void merge (int &t, int l, int r) {
if (!l && !r) { t = 0; return; }
if (!l || !r) t = l? l: r;
else {
createNew(); t = getLst();
item *ptr = &T[t];
if (T[l].prior > T[r].prior) {
T[t] = T[l];
merge (T[t].r, T[l].r, r);
} else {
T[t] = T[r];
merge (T[t].l, l, T[r].l);
}
if (&T[t] != ptr)
printf("I was %p but now am %p\n", ptr, &T[t]);
}
upd_cnt (t);
}
void split (int t, int &l, int &r, int key, int add = 0) {
if (!t)
return void( l = r = 0 );
int cur_key = add + cnt(T[t].l);
createNew(); int tmp = getLst();
T[tmp] = T[t];
if (key <= cur_key)
split (T[t].l, l, T[tmp].l, key, add), r = tmp;
else
split (T[t].r, T[tmp].r, r, key, add + 1 + cnt(T[t].l)), l = tmp;
upd_cnt (tmp);
}
void Modify(int &t, int old, int ind, int nval)
{
createNew(); t = getLst();
T[t] = T[old];
int bef = cnt(T[old].l);
if (ind < bef) Modify(T[t].l, T[old].l, ind, nval);
else if (ind == bef) T[t].myval = nval;
else Modify(T[t].r, T[old].r, ind - bef - 1, nval);
upd_cnt(t);
}
void Count(int t, int hm, int res[])
{
if (!t) return;
int bef = cnt(T[t].l);
if (hm < bef) { Count(T[t].l, hm, res); return; }
if (T[t].l)
for (int i = 0; i < Maxb; i++)
res[i] += T[T[t].l].val[i];
hm -= bef;
if (hm < 1) return;
res[T[t].myval]++;
hm--;
Count(T[t].r, hm, res);
}
int main()
{
srand(time(0));
createNew(); // dummy
scanf("%d", &n);
for (int i = 1; i <= n; i++) {
scanf("%s", tmp); tlen = strlen(tmp);
for (int j = 0; j < tlen; j++) {
createNew(bases.find(tmp[j])); int add = getLst();
merge(my[i], my[i], add);
}
}
scanf("%d", &q);
while (q--) {
scanf("%s", tmp);
if (tmp[1] == 'R') { // Cross
int id1, id2, k1, k2; scanf("%d %d %d %d", &id1, &id2, &k1, &k2);
int A, B; split(my[id1], A, B, k1);
int C, D; split(my[id2], C, D, k2);
merge(my[++n], A, D);
merge(my[++n], C, B);
} else if (tmp[1] == 'U') { // Mutate
int id, k; char m; scanf("%d %d %c", &id, &k, &m);
Modify(my[id], my[id], k - 1, bases.find(m));
} else if (tmp[1] == 'O') { // Count
int id, k1, k2; scanf("%d %d %d", &id, &k1, &k2);
fill(A, A + Maxb, 0); fill(B, B + Maxb, 0);
Count(my[id], k2, B); Count(my[id], k1 - 1, A);
for (int i = 0; i < Maxb; i++)
printf("%d%c", B[i] - A[i], i + 1 < Maxb? ' ': '\n');
}
}
return 0;
}
I2luY2x1ZGUgPGJpdHMvc3RkYysrLmg+CnVzaW5nIG5hbWVzcGFjZSBzdGQ7Cgpjb25zdCBzdHJpbmcgYmFzZXMgPSAiQUdUQyI7CmNvbnN0IGludCBNYXhiID0gNDsKY29uc3QgaW50IE1heG4gPSA3MDAwNTsKCnN0cnVjdCBpdGVtIHsKCWludCBwcmlvciwgbXl2YWwsIHZhbFtNYXhiXSwgY250OwoJaW50IGwsIHI7CglpdGVtKGludCBteXZhbCA9IDApOiBwcmlvcihyYW5kKCkpLCBjbnQoMSksIG15dmFsKG15dmFsKSwgbCgwKSwgcigwKSB7CgkgICAgZmlsbCh2YWwsIHZhbCArIE1heGIsIDApOwoJICAgIHZhbFtteXZhbF0rKzsKICAgIH0KfTsKCmNoYXIgdG1wW01heG5dOwppbnQgdGxlbjsKdmVjdG9yIDxpdGVtPiBUOwppbnQgbjsKaW50IG15W01heG5dOwppbnQgcTsKaW50IEFbTWF4Yl0sIEJbTWF4Yl07Cgp2b2lkIGNyZWF0ZU5ldyhpbnQgdmFsID0gMCkgeyBULnB1c2hfYmFjayhpdGVtKHZhbCkpOyB9CgppbnQgZ2V0THN0KCkgeyByZXR1cm4gaW50KFQuc2l6ZSgpKSAtIDE7IH0KCmludCBjbnQgKGludCBpdCkgewoJcmV0dXJuIGl0ID8gVFtpdF0uY250OiAwOwp9Cgp2b2lkIHVwZF9jbnQgKGludCBpdCkgewoJaWYgKGl0KSB7CgkJVFtpdF0uY250ID0gY250KFRbaXRdLmwpICsgY250KFRbaXRdLnIpICsgMTsKCQlmb3IgKGludCBpID0gMDsgaSA8IE1heGI7IGkrKykKICAgICAgICAgICAgVFtpdF0udmFsW2ldID0gKFRbaXRdLmw/IFRbVFtpdF0ubF0udmFsW2ldOiAwKSArCiAgICAgICAgICAgICAgICAgICAgICAgICAgIChUW2l0XS5yPyBUW1RbaXRdLnJdLnZhbFtpXTogMCk7CiAgICAgICAgVFtpdF0udmFsW1RbaXRdLm15dmFsXSsrOwoJfQp9Cgp2b2lkIG1lcmdlIChpbnQgJnQsIGludCBsLCBpbnQgcikgewogIGlmICghbCAmJiAhcikgeyB0ID0gMDsgcmV0dXJuOyB9CiAgaWYgKCFsIHx8ICFyKSB0ID0gbD8gbDogcjsKICBlbHNlIHsKICAgIGNyZWF0ZU5ldygpOyB0ID0gZ2V0THN0KCk7CiAgICBpdGVtICpwdHIgPSAmVFt0XTsKICAgIGlmIChUW2xdLnByaW9yID4gVFtyXS5wcmlvcikgewogICAgICBUW3RdID0gVFtsXTsKICAgICAgbWVyZ2UgKFRbdF0uciwgVFtsXS5yLCByKTsKICAgIH0gZWxzZSB7CiAgICAgIFRbdF0gPSBUW3JdOwogICAgICBtZXJnZSAoVFt0XS5sLCBsLCBUW3JdLmwpOwogICAgfQogICAgaWYgKCZUW3RdICE9IHB0cikKICAgIAlwcmludGYoIkkgd2FzICVwIGJ1dCBub3cgYW0gJXBcbiIsIHB0ciwgJlRbdF0pOwogIH0KICB1cGRfY250ICh0KTsKfQoKdm9pZCBzcGxpdCAoaW50IHQsIGludCAmbCwgaW50ICZyLCBpbnQga2V5LCBpbnQgYWRkID0gMCkgewoJaWYgKCF0KQoJCXJldHVybiB2b2lkKCBsID0gciA9IDAgKTsKCWludCBjdXJfa2V5ID0gYWRkICsgY250KFRbdF0ubCk7CgljcmVhdGVOZXcoKTsgaW50IHRtcCA9IGdldExzdCgpOwoJVFt0bXBdID0gVFt0XTsKCWlmIChrZXkgPD0gY3VyX2tleSkKCQlzcGxpdCAoVFt0XS5sLCBsLCBUW3RtcF0ubCwga2V5LCBhZGQpLCAgciA9IHRtcDsKCWVsc2UKCQlzcGxpdCAoVFt0XS5yLCBUW3RtcF0uciwgciwga2V5LCBhZGQgKyAxICsgY250KFRbdF0ubCkpLCAgbCA9IHRtcDsKCXVwZF9jbnQgKHRtcCk7Cn0KCnZvaWQgTW9kaWZ5KGludCAmdCwgaW50IG9sZCwgaW50IGluZCwgaW50IG52YWwpCnsKICAgIGNyZWF0ZU5ldygpOyB0ID0gZ2V0THN0KCk7CiAgICBUW3RdID0gVFtvbGRdOwogICAgaW50IGJlZiA9IGNudChUW29sZF0ubCk7CiAgICBpZiAoaW5kIDwgYmVmKSBNb2RpZnkoVFt0XS5sLCBUW29sZF0ubCwgaW5kLCBudmFsKTsKICAgIGVsc2UgaWYgKGluZCA9PSBiZWYpIFRbdF0ubXl2YWwgPSBudmFsOwogICAgZWxzZSBNb2RpZnkoVFt0XS5yLCBUW29sZF0uciwgaW5kIC0gYmVmIC0gMSwgbnZhbCk7CiAgICB1cGRfY250KHQpOwp9Cgp2b2lkIENvdW50KGludCB0LCBpbnQgaG0sIGludCByZXNbXSkKewogICAgaWYgKCF0KSByZXR1cm47CiAgICBpbnQgYmVmID0gY250KFRbdF0ubCk7CiAgICBpZiAoaG0gPCBiZWYpIHsgQ291bnQoVFt0XS5sLCBobSwgcmVzKTsgcmV0dXJuOyB9CiAgICBpZiAoVFt0XS5sKQogICAgICAgIGZvciAoaW50IGkgPSAwOyBpIDwgTWF4YjsgaSsrKQogICAgICAgICAgICByZXNbaV0gKz0gVFtUW3RdLmxdLnZhbFtpXTsKICAgIGhtIC09IGJlZjsKICAgIGlmIChobSA8IDEpIHJldHVybjsKICAgIHJlc1tUW3RdLm15dmFsXSsrOwogICAgaG0tLTsKICAgIENvdW50KFRbdF0uciwgaG0sIHJlcyk7Cn0KCmludCBtYWluKCkKewogICAgc3JhbmQodGltZSgwKSk7CiAgICBjcmVhdGVOZXcoKTsgLy8gZHVtbXkKICAgIHNjYW5mKCIlZCIsICZuKTsKICAgIGZvciAoaW50IGkgPSAxOyBpIDw9IG47IGkrKykgewogICAgICAgIHNjYW5mKCIlcyIsIHRtcCk7IHRsZW4gPSBzdHJsZW4odG1wKTsKICAgICAgICBmb3IgKGludCBqID0gMDsgaiA8IHRsZW47IGorKykgewogICAgICAgICAgICBjcmVhdGVOZXcoYmFzZXMuZmluZCh0bXBbal0pKTsgaW50IGFkZCA9IGdldExzdCgpOwogICAgICAgICAgICBtZXJnZShteVtpXSwgbXlbaV0sIGFkZCk7CiAgICAgICAgfQogICAgfQogICAgc2NhbmYoIiVkIiwgJnEpOwogICAgd2hpbGUgKHEtLSkgewogICAgICAgIHNjYW5mKCIlcyIsIHRtcCk7CiAgICAgICAgaWYgKHRtcFsxXSA9PSAnUicpIHsgIC8vIENyb3NzCiAgICAgICAgICAgIGludCBpZDEsIGlkMiwgazEsIGsyOyBzY2FuZigiJWQgJWQgJWQgJWQiLCAmaWQxLCAmaWQyLCAmazEsICZrMik7CiAgICAgICAgICAgIGludCBBLCBCOyBzcGxpdChteVtpZDFdLCBBLCBCLCBrMSk7CiAgICAgICAgICAgIGludCBDLCBEOyBzcGxpdChteVtpZDJdLCBDLCBELCBrMik7CiAgICAgICAgICAgIG1lcmdlKG15Wysrbl0sIEEsIEQpOwogICAgICAgICAgICBtZXJnZShteVsrK25dLCBDLCBCKTsKICAgICAgICB9IGVsc2UgaWYgKHRtcFsxXSA9PSAnVScpIHsgIC8vIE11dGF0ZQogICAgICAgICAgICBpbnQgaWQsIGs7IGNoYXIgbTsgc2NhbmYoIiVkICVkICVjIiwgJmlkLCAmaywgJm0pOwogICAgICAgICAgICBNb2RpZnkobXlbaWRdLCBteVtpZF0sIGsgLSAxLCBiYXNlcy5maW5kKG0pKTsKICAgICAgICB9IGVsc2UgaWYgKHRtcFsxXSA9PSAnTycpIHsgIC8vIENvdW50CiAgICAgICAgICAgIGludCBpZCwgazEsIGsyOyBzY2FuZigiJWQgJWQgJWQiLCAmaWQsICZrMSwgJmsyKTsKICAgICAgICAgICAgZmlsbChBLCBBICsgTWF4YiwgMCk7IGZpbGwoQiwgQiArIE1heGIsIDApOwogICAgICAgICAgICBDb3VudChteVtpZF0sIGsyLCBCKTsgQ291bnQobXlbaWRdLCBrMSAtIDEsIEEpOwogICAgICAgICAgICBmb3IgKGludCBpID0gMDsgaSA8IE1heGI7IGkrKykKICAgICAgICAgICAgICAgIHByaW50ZigiJWQlYyIsIEJbaV0gLSBBW2ldLCBpICsgMSA8IE1heGI/ICcgJzogJ1xuJyk7CiAgICAgICAgfQogICAgfQogICAgcmV0dXJuIDA7Cn0=