[POI2012] OKR-A Horrible Poem 题解
前言
题目链接:洛谷。
题意简述
给出长度为
题目分析
联想到 KMP 求循环节的过程,如果
字符串相等的过程,可以用字符串哈希
发现
当然还可以继续优化。
发现,如果
即,将
由于
预处理可以用线性筛
代码
略去了快读快写。卡卡常最优解。
#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; }
本文作者:XuYueming,转载请注明原文链接:https://www.cnblogs.com/XuYueming/p/18326726。
若未作特殊说明,本作品采用 知识共享署名-非商业性使用 4.0 国际许可协议 进行许可。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 单线程的Redis速度为什么快?
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 展开说说关于C#中ORM框架的用法!