【BZOJ-2342】双倍回文 Manacher + 并查集
2342: [Shoi2011]双倍回文
Time Limit: 10 Sec Memory Limit: 128 MB
Submit: 1799 Solved: 671
[Submit][Status][Discuss]
Description
Input
输入分为两行,第一行为一个整数n,表示字符串的长度,第二行有n个连续的小写的英文字符,表示字符串的内容。
Output
输出文件只有一行,即:输入数据中字符串的最长双倍回文子串的长度,如果双倍回文子串不存在,则输出0。
Sample Input
ggabaabaabaaball
Sample Output
HINT
N<=500000
Source
Solution
看完题大体的思路就是先一遍Manacher,O(n)求出回文串,然后进行判断
题目中说的很清楚,双倍回文串长度一定是4的倍数,即为偶数,那么Manacher出来的回文串中心一定在字符间添加的'#'上
那么考虑要求的东西 y+p[y]>=x && y>=x-p[x]/2,思考一个枚举的方法
枚举j,如果j不能覆盖到当前的i,那么一定是不符合覆盖到i+1的,所以,之后的所有事和它无关,可以忽略,这样想,维护一下就好了,采取并查集
Code
#include<iostream> #include<cstdio> #include<cstring> #include<algorithm> #include<cmath> using namespace std; #define maxn 500010 char S[maxn],s[maxn<<1]; int n,len,mx,id,p[maxn<<1],fa[maxn<<1],ans; void PreWork() {memset(p,0,sizeof(p));len=n<<1|1;for (int i=1; i<=n; i++)s[i<<1]=S[i],s[i<<1|1]='#';s[0]='$'; s[1]='#'; s[len+1]='%'; } void Manacher() {PreWork();for (int i=1; i<=len; i++){if (mx>i) p[i]=min(p[id*2-i],mx-i);else p[i]=1;while (s[i-p[i]]==s[i+p[i]]) p[i]++;if (p[i]+i>mx) mx=p[i]+i,id=i;} } int find(int x) {if (fa[x]==x) return x; else return fa[x]=find(fa[x]);} int main() {scanf("%d",&n); scanf("%s",S+1);Manacher();for (int i=1; i<=len; i++)if (s[i]=='#') fa[i]=i; else fa[i]=i+1;for (int i=3; i<=len-1; i+=2){int f=find(max(i-p[i]/2,1));while (f<i && f+p[f]<i) fa[f]=find(f+1),f=fa[f];if (f<i && (i-f)*2>ans) ans=(i-f)*2; }printf("%d\n",ans);return 0; }
转载于:https://www.cnblogs.com/DaD3zZ-Beyonder/p/5528671.html
【BZOJ-2342】双倍回文 Manacher + 并查集相关推荐
- bzoj 2342: 双倍回文 回文自动机
题目大意: 定义双倍回文串的左一半和右一半均是回文串的长度为4的倍数的回文串 求一个给定字符串中最长的双倍回文串的长度 题解: 我们知道可以简单地判定以某一点结尾的最长回文串 我们知道可以简单地判定以 ...
- 洛谷-P4287 双倍回文(Manacher)
双倍回文 Manacher算法用的还是不够熟悉啊,被卡了好久...一会再写个回文自动机的做法吧 清晰的回文自动机写法 题意:若一个回文串左半部分和有半部分分别为一个回文串,则这个回文串被称为双倍回文串 ...
- [SHOI2011]双倍回文 manacher
题面: 洛谷:[SHOI2011]双倍回文' 题解: 首先有一个性质,本质不同的回文串最多O(n)个. 所以我们可以对于每个i,求出以这个i为结尾的最长回文串,然后以此作为长串,并判断把这个长串从中间 ...
- HYSBZ - 2342 双倍回文(回文自动机)
题目链接:点击查看 题目大意:给出一个字符串 s ,求最长双倍回文子串,题目规定双倍回文子串是长度可以被4整除,且前半段.后半段以及整个字串都是回文串 题目分析:因为在构造回文自动机时,连接的失配边就 ...
- BZOJ 2342 [Shoi2011]双倍回文(manacher+并查集)
[题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=2342 [题目大意] 记Wr为W串的倒置,求最长的形如WWrWWr的串的长度. [题解] ...
- 「BZOJ 2342」「SHOI 2011」双倍回文「Manacher」
题意 记\(s_R\)为\(s\)翻转后的串,求一个串最长的形如\(ss_Rss_R\)的子串长度 题解 这有一个复杂度明显\(O(n)\)的做法,思路来自网上某篇博客 一个双倍回文串肯定当且仅当本身 ...
- 【BZOJ2342】双倍回文,manacher+并查集优化
Time:2016.08.16 Author:xiaoyimi 转载注明出处谢谢 传送门 思路: woc第一次写马拉车怎么这么蛋疼啊 p[i]表示以i为中点,能向增长的最多的回文长度的一半 比如&qu ...
- BZOJ 2342: 【SHOI2011】 双倍回文
题目链接:双倍回文 回文自动机第二题.构出回文自动机,那么一个回文串是一个"双倍回文",当且仅当代表这个串的节点\(u\)顺着\(fail\)指针往上跳,可以找到一个节点\(x\) ...
- [BZOJ2342] [Shoi2011]双倍回文(manacher)
传送门 manacher...... 先跑一边manacher是必须的 然后枚举双倍回文串的对称轴x 把这个双倍回文串分成4段,w wR w wR 发现,只有当 y <= x + p[x] / ...
最新文章
- Chapter5_初始化与清理_enum关键字
- python模块学下urllib
- Golang入门教程(十七)Linux/Windows下快速搭建和配置NSQ
- easyUi创建临时Dialog
- Fragment Summary 2/2
- eclipse error pages打红X的解决方法
- flink 复杂事件_复杂的(事件)世界
- LeetCode 23. 合并K个排序链表(优先队列)
- C++中 #define的用法
- 黑匣子解密要多久_科普|飞机上的黑匣子内置电池可工作多久?
- java发送短信的发送报告处理
- led显示屏背景墙设计_西安盛泉广告设计制作||发光字标识,门头广告牌,灯箱,LED显示屏...
- ALV 行、列、单元格颜色设置
- Android deeplink原理解析
- 边缘之战鸣枪 新华三蓄势待发
- Docker Mysql使用学习
- 如何在信息不完备下进行快速决策?
- Windows图标-Icon文件格式分析
- 中国移动电视显示android,中国移动电视机无线网络连接不上啥起因
- 树莓派摄像头无法识别 mmal
热门文章
- asp.net网页出现名称以无效字符开头的解决方法
- CSP:CSP认证考试:202109-1(数组推导)满分答案,Java版
- 【LeetCode】198.打家劫舍
- mysql replace报错_Mysql中replace与replace into的用法讲解
- idea mybatis generator插件_在idea中使用mybatis generator逆向工程生成代码
- 联想m7400pro更换墨粉盒怎么清零_打印耗材到底怎么选
- ipython官网_IPython Notebook快速搭建
- CUDA support is required (OpenCV CMake parameter ‘WITH_CUDA‘ must be true).
- opencv_contrib编译失败解决方法
- OpenStack Pike Minimal安装:三、镜像管理