intqpow(int bs, int64_t idx = kMod - 2){ int ret = 1; for (; idx; idx >>= 1, bs = (int64_t)bs * bs % kMod) if (idx & 1) ret = (int64_t)ret * bs % kMod; return ret; }
inlineintadd(int x, int y){ return (x + y >= kMod ? x + y - kMod : x + y); } inlineintsub(int x, int y){ return (x >= y ? x - y : x - y + kMod); } inlinevoidinc(int &x, int y){ (x += y) >= kMod ? x -= kMod : x; } inlinevoiddec(int &x, int y){ (x -= y) < 0 ? x += kMod : x; }
intsolve(int m, int *a){ staticint f[kMaxN], d[kMaxN], nxt[kMaxN]; if (m == 1) return a[m] - 1; std::function<void()> getnxt = [&] () { for (int o = 0; o < 2; ++o) { staticint stk[kMaxN]; int top = 0; stk[0] = m + 1; for (int i = m - (m % 2 != o); i >= 1; i -= 2) { for (; top && a[i] - i / 2 >= a[stk[top]] - stk[top] / 2; --top) {} nxt[i] = stk[top], stk[++top] = i; } } }; getnxt(); f[1] = a[1]; for (int i = 0; i <= m; ++i) d[i] = 0; for (int i = 2; i <= m; ++i) f[i] = (i & 1); int ret = 0; for (int i = 1; i <= m - 1; ++i) { if (i >= 3) inc(d[i], d[i - 2]); inc(f[i], d[i]); if (i % 2 == (m - 1) % 2) inc(ret, f[i]); for (int j = i + 1, lim = 0; j <= m - 1; lim += (nxt[j] - j) / 2 - 1, j = nxt[j]) { inc(f[j], 1ll * f[i] * (std::max(lim + 1, a[j]) - lim) % kMod); assert(a[j] >= lim + 1); lim = std::max(lim + 1, a[j]); if (j + 2 < nxt[j]) { inc(d[j + 2], f[i]), dec(d[nxt[j]], f[i]); // for (int k = j + 2; k < nxt[j]; k += 2) { // assert(lim + 1 >= a[k]); // inc(f[k], f[i]); // lim = std::max(lim + 1, a[k]); // } } } // for (int j = i + 1, lim = 0; j <= m - 1; j += 2) { // inc(f[j], 1ll * f[i] * (std::max(lim + 1, a[j]) - lim) % kMod); // lim = std::max(lim + 1, a[j]); // } } return1ll * ret * a[m] % kMod; }
voiddickdreamer(){ std::cin >> n >> str; m = 0; for (int i = 0, lst = -1; i < n; ++i) { if (i == n - 1 || str[i] != str[i + 1]) a[++m] = i - lst, lst = i; } int ans = solve(m, a); if (n >= 2) { a[2] = 1; inc(ans, solve(m - 1, a + 1)); } std::cout << ans << '\n'; }