#include #include #include #include using namespace std; const int maxn = 100001; string s; vector segment_tree[3 * maxn]; void build(int L, int R, int node) { if(L == R) { cout << L << " " << node<< endl; segment_tree[node][s[L] - 'a']++; return; } int mid = (L + R) / 2; build(L, mid, 2 * node); build(mid + 1, R, 2 * node + 1); for(int i = 0; i < 26; i++) { segment_tree[node][i] = segment_tree[2 * node][i] + segment_tree[2 * node + 1][i]; } } vector my_merge(vector a, vector b) { vector c(26, 0); for(int i = 0; i < 26; i++) { c[i] = a[i] + b[i]; } return c; } vector query(int L, int R, int node, int i, int j) { // L R i L R j L R if(i <= L and R <= j) { return segment_tree[node]; } if(R < i or j < L) { return vector(26, 0); } int mid = (L + R) / 2; return my_merge(query(L, mid, 2 * node, i, j), query(mid + 1, R, 2 * node + 1, i, j)); } void update(int L, int R, int node, int idx, char c_val, char n_val) { if(L == R) { segment_tree[node][c_val - 'a']--; segment_tree[node][n_val - 'a']++; return; } int mid = (L + R) / 2; if(idx <= mid) { update(L, mid, 2 * node, idx, c_val, n_val); } else { update(mid + 1, R, 2 * node + 1, idx, c_val, n_val); } for(int i = 0; i < 26; i++) { segment_tree[node][i] = segment_tree[2 * node][i] + segment_tree[2 * node + 1][i]; } } int main() { for(int i = 0; i < 3 * maxn; i++) { segment_tree[i] = vector(26, 0); } cin >> s; int n = (int) s.size(); build(0, n - 1, 1); int q; cin >> q; while(q--) { int type; cin >> type; if(type == 2) { int L, R; cin >> L >> R; string tmp; cin >> tmp; vector freq = query(0, n - 1, 1, L, R); long long res = 1; for(int i =0 ; i < 26; i++) { if(freq[i] > 0) { cout << (char) (i + 'a') << " " << freq[i] << endl; } } for(int i = 0; i < tmp.size(); i++) { res *= freq[tmp[i] - 'a']; res %= 1000000007; } cout << res << endl; } else { int idx; char c; cin >> idx >> c; update(0, n - 1, 1, idx, s[idx], c); s[idx] = c; } } return 0; } // gxeekkksgskeegks // 1 7 gek /* geeekkksgskeegks 3 2 0 6 gek */