[POI2012] OKR-A Horrible Poem 题解

前言

题目链接:洛谷

题意简述

给出长度为 nn5×105)的字符串 Sqq2×106)询问某一子串的最短循环节。AB 的循环节,当 B 可以由 A 重复若干次拼接成。

题目分析

联想到 KMP 求循环节的过程,如果 lenS 的循环节长度,那么一定有 S[1nlen]=S[len+1n],以及 lenn。当然,只有本身为循环节的话,len=n

字符串相等的过程,可以用字符串哈希 Θ(n)Θ(1) 地搞。但是枚举 lenΘ(n) 的,时间复杂度 Θ(n+qn),考虑优化。

发现 q 不和 n 同阶,所以想到预处理出每个数的所有因子。预处理用埃氏筛,时间复杂度 Θ(nlogn),枚举的时候取决于因子最多的个数,记为 k,在本题数据范围,应为 k=200。时间复杂度 Θ(nlogn+qk),能过本题。

当然还可以继续优化。

发现,如果 len 是答案,那么 klen 肯定也是答案。而 len=n 肯定是答案。所以考虑反过来计算。

即,将 n 分解成 piki,答案 len=piki。初始 ki=ki,那么每次就是尝试将一个 kiki1,如果得到的 len 是一个合法循环节长度,那就减掉。

由于 ki 之间互不影响,从小的质因数开始尝试。记 f(x) 表示 x 的最小质因数。设 ans=len,然后循环判断 ansf(len) 能否成为新的答案,可以就让 ansansf(len)。然后 lenlenf(len)。直到 len=1。这里 lenf(len) 就是在不断搞最小质因数的过程。

预处理可以用线性筛 Θ(n) 地搞。查询的时候,时间复杂度是 Θ(ki)O(logn)。总的时间复杂度 O(n+qlogn)

代码

略去了快读快写。卡卡常最优解

#include <cstdio>
#include <algorithm>
using namespace std;
int n, q;
char str[500010];
using ull = unsigned long long;
int hav[500010], pri[500010], pcnt;
ull hsh[500010], pw[500010];
inline ull get_hash(int l, int r) {
if (l > r) return 0;
return hsh[r] - hsh[l - 1] * pw[r - l + 1];
}
signed main() {
fread(buf, 1, MAX, stdin);
read(n);
for (int i = 2; i <= n; ++i) {
if (!hav[i]) hav[i] = pri[++pcnt] = i;
for (int j = 1; j <= pcnt && i * pri[j] <= n; ++j) {
hav[i * pri[j]] = pri[j];
if (i % pri[j] == 0) break;
}
}
pw[0] = 1;
for (register int i = 1; i <= n; ++i) {
do str[i] = getchar(); while (str[i] < 'a' || str[i] > 'z');
hsh[i] = (hsh[i - 1] * 131 + str[i] - 'a' + 11);
pw[i] = pw[i - 1] * 131;
}
read(q);
for (register int i = 1, l, r; i <= q; ++i) {
read(l), read(r);
if (get_hash(l, r - 1) == get_hash(l + 1, r)) {
write(1), putchar('\n');
continue;
}
int ans = r - l + 1, len = ans;
while (len > 1) {
if (get_hash(l, r - ans / hav[len]) == get_hash(l + ans / hav[len], r))
ans /= hav[len];
len /= hav[len];
}
write(ans), putchar('\n');
}
fwrite(obuf, 1, o - obuf, stdout);
return 0;
}
posted @   XuYueming  阅读(47)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 单线程的Redis速度为什么快?
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 展开说说关于C#中ORM框架的用法!
点击右上角即可分享
微信分享提示