前言

题目链接:洛谷

题意简述

给出长为 \(n\) 的串 \(\texttt{S}\)。求最大的 \(l\) 满足:

\[2l \leq n \land \texttt{S}[1 \ldots l] \doteq \texttt{S}[n - l + 1 \ldots n]
\]

其中 \(\doteq\) 表示循环相同。

题目分析

看到循环相同,套路化想到,两个字符串一定可以表示成 \(\texttt{AB}\) 和 \(\texttt{BA}\) 的形式。那么 \(\texttt{S}\) 就能表示成 \(\texttt{ABTBA}\)。那么可以枚举两侧的 \(\texttt{A}\),接下来问题变成了求 \(\texttt{S}\) 扣掉两侧的 border。

求 border,想到每次线性跑一遍 KMP,但是这样是 \(\Theta(n^2)\),能够得到 \(50 \%\) 的部分分。考虑优化。

发现 \(i \sim n - i + 1\) 的 border 和 \(i - 1 \sim n - i\) 的 border 在某些情况下有很大一部分是重合的。进一步发现,从前者到后者,border 最多增加 \(2\),如图。

淡蓝色的是 \(i \sim n - i + 1\) 的 border,\(i - 1 \sim n - i\) 的 border 在此基础上多了红色和绿色部分。

所以考虑递推。记 \(f_i\) 表示 \(\texttt{S}\) 删去前 \(i\) 个和后 \(i\) 个字符的 border。边界 \(f_{\Big \lfloor \cfrac{n}{2} \Big \rfloor + 1} = 0\)。每次 \(f_i\) 初始值设置成 \(f_{i + 1} + 2\),当然需要和 \(\Big \lfloor \cfrac{n}{2} \Big \rfloor - i\) 取个 \(\min\)。然后一直让 \(f_i \gets f_i - 1\),直到满足找到一个长为 \(f_i\) 的 border,这样显然是最优的。

至于判断是否为 border,使用哈希即可。

时间复杂度的话,把 \(f\) 看成不断 \(+2\) 和 \(-1\),前者次数不会超过 \(\Big \lfloor \cfrac{n}{2} \Big \rfloor\),所以是 \(\Theta(n)\) 的。

代码

// #pragma GCC optimize(3)
// #pragma GCC optimize("Ofast", "inline", "-ffast-math")
// #pragma GCC target("avx", "sse2", "sse3", "sse4", "mmx")
#include <iostream>
#include <cstdio>
#define debug(a) cerr << "Line: " << __LINE__ << " " << #a << endl
#define print(a) cerr << #a << "=" << (a) << endl
#define file(a) freopen(#a".in", "r", stdin), freopen(#a".out", "w", stdout)
#define main Main(); signed main() { return ios::sync_with_stdio(0), cin.tie(0), Main(); } signed Main
using namespace std; const int mod = 1314736520;
const int bas = 131; inline int add(int a, int b) {
return a + b >= mod ? a + b - mod : a + b;
} inline int sub(int a, int b) {
return a - b < 0 ? a - b + mod : a - b;
} inline int mul(int a, int b) {
return 1ll * a * b % mod;
} int n, hsh[1000010], pw[1000010];
char str[1000010]; int f[1000010], ans; inline int gethash(int l, int r) {
return l > r ? 0 : sub(hsh[r], mul(hsh[l - 1], pw[r - l + 1]));
} signed main() {
scanf("%d%s", &n, str + 1), pw[0] = 1;
for (int i = 1; i <= n; ++i) {
hsh[i] = add(mul(hsh[i - 1], bas), str[i]);
pw[i] = mul(pw[i - 1], bas);
}
for (int i = n / 2; i >= 1; --i) {
int res = min(f[i + 1] + 2, n / 2 - i);
while (res >= 1 && gethash(i + 1, i + res) != gethash(n - i - res + 1, n - i))
--res;
f[i] = res;
}
for (int i = 1; i <= n / 2; ++i)
if (gethash(1, i) == gethash(n - i + 1, n))
ans = max(ans, i + f[i]);
printf("%d\n", ans);
return 0;
}

[POI2012] PRE-Prefixuffix 题解的更多相关文章

  1. POI2012题解

    POI2012题解 这次的完整的\(17\)道题哟. [BZOJ2788][Poi2012]Festival 很显然可以差分约束建图.这里问的是变量最多有多少种不同的取值. 我们知道,在同一个强连通分 ...

  2. 【BZOJ2803】[Poi2012]Prefixuffix 结论题

    [BZOJ2803][Poi2012]Prefixuffix Description 对于两个串S1.S2,如果能够将S1的一个后缀移动到开头后变成S2,就称S1和S2循环相同.例如串ababba和串 ...

  3. [BZOJ2803][Poi2012]Prefixuffix

    2803: [Poi2012]Prefixuffix Time Limit: 10 Sec  Memory Limit: 64 MBSubmit: 219  Solved: 95[Submit][St ...

  4. bzoj 2803 [Poi2012]Prefixuffix 兼字符串hash入门

    打cf的时候遇到的问题,clairs告诉我这是POI2012 的原题..原谅我菜没写过..于是拐过来写这道题并且学了下string hash.   字符串hash基于Rabin-Karp算法,并且对于 ...

  5. [Poi2012]Festival 题解

    [Poi2012]Festival 时间限制: 1 Sec  内存限制: 64 MB 题目描述 有n个正整数X1,X2,...,Xn,再给出m1+m2个限制条件,限制分为两类: 1. 给出a,b (1 ...

  6. 题解:POI2012 Salaries

    题解:POI2012 Salaries Description The Byteotian Software Corporation (BSC) has \(n\) employees. In BSC ...

  7. BZOJ2803[Poi2012]Prefixuffix——hash

    题目描述 对于两个串S1.S2,如果能够将S1的一个后缀移动到开头后变成S2,就称S1和S2循环相同.例如串ababba和串abbaab是循环相同的.给出一个长度为n的串S,求满足下面条件的最大的L: ...

  8. 【题解】 [POI2012]FES-Festival (差分约束)

    懒得复制题面,戳我戳我 Question: (因为网上找不到好的翻译,这里简单复述一下) 告诉你\(m1+m2\)个约束条件,然后要你找出\(X_1-X_n\)这些数字,求满足要求的数列中不同的数字个 ...

  9. bzoj 2803 [POI2012]prefixuffix hsh+性质

    题目大意 bzoj 2803 对于两个串S1.S2,如果能够将S1的一个后缀移动到开头后变成S2,就称S1和S2循环相同.例如串ababba和串abbaab是循环相同的. 给出一个长度为n的串S,求满 ...

  10. 2016 华南师大ACM校赛 SCNUCPC 非官方题解

    我要举报本次校赛出题人的消极出题!!! 官方题解请戳:http://3.scnuacm2015.sinaapp.com/?p=89(其实就是一堆代码没有题解) A. 树链剖分数据结构板题 题目大意:我 ...

随机推荐

  1. Linux虚拟网卡TUN和TAP

    简介 在 Linux 网络管理中,虚拟网卡(Virtual Network Interface)是一个重要的概念,广泛应用于虚拟化.网络仿真和隧道技术中.本文将重点介绍 TUN(Network TUN ...

  2. java8 lambda Predicate示例

    import java.util.Arrays; import java.util.List; import java.util.function.Predicate; public class Pr ...

  3. 《Vue3.x +TpyeScript实践指南》勘误

    图书出版已有一段时间,书中已发现错误如下: 书的第14页,倒数第3行,npm init -y命令中,init和-y之间应该有个空格: 书的第32页,代码的第1行,应该为模板字符串符号 `,我看印刷的是 ...

  4. DDD 笔记

    1. 简单讲讲DDD,和DDD哪些优势 领域驱动设计.就是通过领域来指导软件设计,是一种十分抽象的软件设计思想,它主要分为战略设计和战术设计 战略方面,通过事件风暴进行领域模型的划分,划分出核心域,子 ...

  5. QT学习:06 常用的全局变量与宏定义

    --- title: framework-cpp-qt-06-常用的全局变量与宏定义 EntryName: framework-cpp-qt-06-global date: 2020-04-10 11 ...

  6. 逆向通达信 x 逆向微信 x 逆向Qt

    本篇在博客园地址https://www.cnblogs.com/bbqzsl/p/18252961 本篇内容包括: win32窗口嵌入Qt UI.反斗玩转signal-slot.最后 通达信 x 微信 ...

  7. .Net Core WebAPI Swagger Failed to load API definition

    1.错误现象 1.1.写完一个测试API,Ctrl+F5运行,提示错误: Failed to load API definition.(如下图) 1.2.点击 http://localhost:516 ...

  8. The Beauty of Physics

    绪言/1 学物理的人用不着对物理方程的意义操心,只要关心物理方程的美就够了. --狄拉克 此曲只应天上有--开普勒的和谐宇宙/11 天体的运动只不过是某种永恒的复调音乐而已,要用才智而不是耳朵来倾听. ...

  9. VulnHub_DC-1渗透流程

    DC-1 DC-1 是一个专门建造的易受攻击的实验室,目的是在渗透测试领域获得经验. 它旨在为初学者提供挑战,但它的难易程度取决于您的技能和知识,以及您的学习能力. 要成功完成此挑战,您将需要 Lin ...

  10. yb课堂之订单列表接口开发 《十七》

    订单列表接口开发 VideoOrderController.java VideoOrderService.java VideoOrderServiceImpl.java VideoOrderMappe ...