manacher算法 详解+模板
manacher算法可以解决字符串的回文子串长度问题。
个人感觉szy学长讲的非常好,讲过之后基本上就理解了。
那就讲一下个人的理解。(参考了szy学长的ppt)
如果一个回文子串的长度是偶数,对称轴会落在两个字符中间。
首先两个字符中间的这个位置就很难表示。
所以我们在两个字符中间加上没有用的字符,比如说'#'。开头结尾也加上。
例如:abcba --> #a#b#c#b#a#
这样我们能很方便的表示每一个位置。
manacher算法最终的目的是求出一个数组pl[i],代表以i为回文中心(也就是对称轴)的最长回文子串的回文半径。
回文半径指的是回文子串的长度除以二之后向上取整。
比如:#a#b#a#的回文半径就是4。
考虑用递推的方法求出pl数组。
首先我们知道pl[1]=1(特殊记一下)。
在递推的过程中维护一个np表示使i+pl[i]最大的一个i。
计算f[i]的时候,先考虑使用已知的信息求出f[i]。
如果i<=np+pl[np],意味着i被以np为回文中心的最长回文子串“覆盖”了。
下面的图用红色表示以np为回文中心的最长回文子串,用绿色表示以i为回文中心的最长回文子串。
这时有两种情况:
1.不仅i被覆盖,以i为回文中心的最长回文子串也被完全覆盖了。

这个时候由于对称性,pl[i]=pl[2*np-i]。
2.虽然i被覆盖,但是以i为回文中心的最长回文子串没有被完全覆盖。

这个时候我们只能保证np+pl[np]以内的对称性(蓝色部分)。
也就是说,pl[i]=pl[np]+np-i。
我们并不知道是哪种情况,所以只能对这两种情况分别求值并取其中的最小值。
之后如果还能继续向外拓展回文部分,就类似暴力的做法,一下一下向外拓展。
最后更新一下np。
求出的pl是适用于新串的(就是混了一堆‘#’的那个串)。
不难发现,对于原串,以i为中心的最长回文子串的长度为pl[i]-1,这个串的开始位置为(i-pl[i])/2+1(向下取整)。
来一道模板题练练:洛谷 P3805 【模板】manacher算法
这里不得不说,szy学长给的代码真是又简洁又明了。
吊打网上那些参杂各种特判的冗长又难读的代码。
膜拜orz。
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std; int n;
char a[];
char s[];
int pl[]; int main()
{
scanf("%s",a+);
int al=strlen(a+);
for(int i=;i<=al;i++)
s[++n]='#',s[++n]=a[i];
s[++n]='#';
int np=;
pl[]=;
for(int i=;i<=n;i++)
{
pl[i]=min(pl[*np-i],pl[np]+np-i);
for(;i+pl[i]<=n&&s[i+pl[i]]==s[i-pl[i]];pl[i]++);
if(i+pl[i]>np+pl[np])np=i;
}
int ans=;
for(int i=;i<=n;i++)ans=max(ans,pl[i]-);
printf("%d",ans);
return ;
}
manacher算法 详解+模板的更多相关文章
- manacher算法详解+模板 P3805
前言: 记住manacher是一个很简单的算法. 首先我们来了解一下回文字串的定义:若一个字符串中的某一子串满足回文的性质,则称其是回文子串.(注意子串必须是连续的,而子序列是可以不连续的) 那么若给 ...
- 算法进阶面试题01——KMP算法详解、输出含两次原子串的最短串、判断T1是否包含T2子树、Manacher算法详解、使字符串成为最短回文串
1.KMP算法详解与应用 子序列:可以连续可以不连续. 子数组/串:要连续 暴力方法:逐个位置比对. KMP:让前面的,指导后面. 概念建设: d的最长前缀与最长后缀的匹配长度为3.(前缀不能到最后一 ...
- Manacher算法详解
问题 什么是回文串,如果一个字符串正着度读和反着读是一样的,这个字符串就被称为回文串. such as noon level aaa bbb 既然有了回文,那就要有关于回文的问题,于是就有了-- 最长 ...
- 经典算法 Manacher算法详解
内容: 1.原始问题 =>O(N^2) 2.Manacher算法 =>O(N) 1.原始问题 Manacher算法是由题目“求字符串中长回文子串的长度”而来.比如 abcdcb 的 ...
- [转] Manacher算法详解
转载自: http://blog.csdn.net/dyx404514/article/details/42061017 Manacher算法 算法总结第三弹 manacher算法,前面讲了两个字符串 ...
- hdu3068之manacher算法+详解
最长回文 Time Limit: 4000/2000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Total Submi ...
- KM算法详解+模板
http://www.cnblogs.com/wenruo/p/5264235.html KM算法用来求二分图最大权完美匹配. 本文配合该博文服用更佳:趣写算法系列之--匈牙利算法 现在有N男N女,男 ...
- KM算法 详解+模板
先说KM算法求二分图的最佳匹配思想,再详讲KM的实现.[KM算法求二分图的最佳匹配思想] 对于具有二部划分( V1, V2 )的加权完全二分图,其中 V1= { x1, x2, x3, ... , x ...
- KMP算法 详解+模板
本文大部分摘自szy学长的ppt<string>中的KMP部分. %%%膜拜szy大神orz 1.概述 KMP 算法是用来解决单模匹配问题的一种算法. 如果暴力的进行单模匹配,那么时间复杂 ...
随机推荐
- solr集群的搭建
solrCloud 昨天随手写了个solr单机版的搭建,今天准备写一个solr集群的搭建!1.solr集群只要环境配置正确还是比较简单的环境:CentOS-6.4-i386-bin-DVD1.isoj ...
- 2018.11.2JavaScript随笔
构造函数首字母大写 通过new创建对象 BOM:浏览器对象模型
- ruoyi LogUtils
package com.ruoyi.framework.util; import java.io.PrintWriter; import java.io.StringWriter; import ja ...
- C++读取数量不定的数据
#include <iostream> using namespace std; int main(){ ,num=; while(cin >> num){//此表达式从标准输 ...
- 基于redis实现锁控制
多数据源 数据源1为锁控制,数据源2自定义,可用于存储. 锁:当出现并发的时候为了保证数据的一致性,不会出现并发问题,假设,用户1修改一条信息,用户2也同时修改,会按照顺序覆盖自修改的值,为了避免这种
- LGOJ3747 六省联考2017 分手是祝愿
这两天遇到不少这种"人类智慧题"了,感觉都是很巧妙的 Description link 现在有 \(n\) 盏灯,设每一次操作控制第 \(i\) 占灯,而改变状态的灯就是 \(i\ ...
- Codeforces 1288D - Minimax Problem
题目大意: 给定n个序列,每个序列元素个数严格相等于m 你需要找到两个序列a[i]和a[j],使其每个对应位置的元素取大后得到b序列 b[k]=max(a[i][k],a[j][k]) 且让b序列中 ...
- 深度学习数据集MNIST ImageNet COCO PASCAL VOC介绍
参考文档 深度学习数据集汇总介绍 1. MNIST 深度学习领域的“Hello World!”,入门必备!MNIST是一个手写数字数据库,它有60000个训练样本集和10000个测试样本集,每个样本 ...
- 吴裕雄--天生自然 pythonTensorFlow图形数据处理:多线程队列操作
import tensorflow as tf #1. 定义队列及其操作. queue = tf.FIFOQueue(100,"float") enqueue_op = queue ...
- kotlin 单例模式
class Single{ companion object { val instance:Single by lazy(mode = LazyThreadSafetyMode.SYNCHRONIZE ...