#define _CRT_SECURE_NO_WARNINGS #pragma comment(linker, "/stack:16777216") #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include using namespace std; #define FOR(i, a, b) for(int i=(a);i<(b);i++) #define RFOR(i, b, a) for(int i=(b)-1;i>=(a);--i) #define FILL(A,value) memset(A,value,sizeof(A)) #define ALL(V) V.begin(), V.end() #define SZ(V) (int)V.size() #define PB push_back #define MP make_pair #define Pi 3.14159265358979 typedef long long Int; typedef unsigned long long UInt; typedef vector VI; typedef pair PII; const int INF = 1000000000; const int MAX = 100007; const int MAX2 = 1000000; const int MAXD = 20; const int BASE = 1000000007; const int MOD = 1000000007; int t[4 * MAX][26]; int p[4 * MAX]; char s[MAX]; int tmp[26]; void rotate(int x, int c) { FOR(i,0,26) { tmp[(i + c) % 26] = t[x][i]; } FOR(i,0,26) { t[x][i] = tmp[i]; } } void push(int v) { if (p[v] == 0) return; p[v] %= 26; p[2 * v + 1] += p[v]; rotate(2 * v + 1 , p[v]); p[2 * v + 2] += p[v]; rotate(2 * v + 2 , p[v]); p[v] = 0; } void build(int v, int l, int r) { if (l == r) { t[v][s[l] - 'a'] = 1; return; } int m = (l + r) / 2; build(2 * v + 1 , l , m); build(2 * v + 2 , m + 1 , r); FOR(i,0,26) t[v][i] = t[2 * v + 1][i] + t[2 * v + 2][i]; } void Update(int v, int l, int r, int L, int R , int c) { if (L > R) return; if (l == L && r == R) { p[v] += c % 26; rotate(v , c % 26); return; } push(v); int m = (l + r) / 2; Update(2 * v + 1 , l , m , L , min(R , m) , c); Update(2 * v + 2 , m + 1 , r , max(L , m + 1) , R , c); FOR(i,0,26) t[v][i] = t[2 * v + 1][i] + t[2 * v + 2][i]; } int C[26]; void Get(int v, int l, int r, int L, int R) { if (L > R) return; if (l == L && r == R) { FOR(i,0,26) { C[i] += t[v][i]; } return; } push(v); int m = (l + r) / 2; Get(2 * v + 1 , l , m , L , min(R , m)); Get(2 * v + 2 , m + 1 , r , max(L , m + 1) , R); } Int pw[MAX]; int main() { //freopen("in.txt" , "r" , stdin); pw[0] = 1; FOR(i,1,MAX) { pw[i] = pw[i - 1] * 2 % MOD; } int n , q; cin >> n >> q; scanf("%s", s); build(0,0,n - 1); FOR(i,0,q) { int t , l , r; scanf("%d%d%d", &t , &l, &r); if (t == 1) { int c; scanf("%d", &c); Update(0, 0, n - 1, l, r, c); } else { FILL(C , 0); Get(0,0,n - 1 , l , r); /*FOR(i,0,26) { cout << C[i] << " "; } cout << endl;*/ Int res = 1; int cnt = 0; FOR(i,0,26) { if (C[i] > 0) { cnt ++; res *= pw[C[i] - 1]; res %= MOD; } } res *= (cnt + 1); res %= MOD; res --; if (res < 0) res += MOD; printf("%d\n", (int)res); } } return 0; }