MANACHER---求最长回文串
求最长回文串,如果是暴力的方法的话,会枚举每个字符为中心,然后向两边检测求出最长的回文串,时间复杂度在最坏的情况下就是0(n^2),为什么时间复杂度会这么高,因为对于每一个作为中心的字符的检测是独立的,没有充分利用前面比较过信息,这就类似暴力求字符串的匹配最糟糕的情况下是0(n*m),然后通过预处理的信息把时间复杂度降低也就是kmp算法;
MANACHER算法:
先假设所有回文串都是以某个字符为中心的,即回文串的长度都是奇数;
lc[ i ]保存的是以位置i的字符为中心的最长回文串到最右边的距离
先假设以知lc[i],(0<=i<x)求lc[x]
设p=k+lc[k]-1,k是使p最大的i的取值,如下图
如果x>p那么直接以x为中心进行检测,并更新k;
如果x<=p那么对于以k为中心x的对称点就是j,并且lc[j]的值已经知道了,
If (lc[j]<p-x+1) lc[x]=lc[j]
因为s[j-1]!=s[j+1], s[j-1]=s[x-1],s[j+1]=s[x+1],所以s[x-1]!=s[x+1]如图:
If (lc[j]>=p-x+1) 那么lc[x]至少是lc[j] 如图:
但对于蓝色位置是不是还需要检测
时间复杂度分析:因为对于每一位s[i]都只被检测了一次,所以是o(n);
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
现在回到最原先的问题,因为回文串有可能是“1221”这种长度是偶数的,MANACHER算法提供了一个构造的方法可以统一这两种情况:在两个字符之间插入一个没有出现过的字符,如‘#’,那么”1221”->”#1#2#2#1#”这样所有的回文串长度都是奇数的了,为了处理方便再在该字符串前面加一个‘$’字符,这样字符串就是$#1#2#2#1#
求出lc[i]后,对于以s[i]为中心的字符串,如果s[i]==’#’,那么len=(lc[i]-1)/2*2,因为lc[i]-1肯定是偶数(因为该回文串的最左和最右肯定是’#’)所以len=lc[i]-1;
如果s[i]!=’#’,那么len=(lc[i] - 1)/2*2+1;因为lc[i]-1肯定是奇数,所以len=lc[i]-2+1=lc[i]-1;
所以最后的解就是最大lc[i]-1;
void Manacher(char *s){
s1[]='$';
int nn=strlen(s),c=;
for (int i=;i<nn;i++){
s1[c++]='#';
s1[c++]=s[i];
}s1[c++]='#';s1[c++]='\0';
// cout<<s<<endl<<s1<<endl; lc[]=;lc[]=;
int k=, p, j;
for (int i=;i<c;i++){
p=k+lc[k]-;
if (p<i){
int t=;
while (i-t>= && i+t<c && s1[i-t]==s1[i+t]) t++;
lc[i]=t; k=i;
}else {
j=*k-i;
if (lc[j]<p-i+) lc[i]=lc[j];
else {
int t=p-i+;
while (i-t>= && i+t<c && s1[i-t]==s1[i+t]) t++;
lc[i]=t; k=i;
}
}
}
int ret=;
for (int i=;i<c;i++){
//cout<<lc[i]<<" ";
if (lc[i]->ret) ret=lc[i]-;
}//cout<<endl;
printf("%d\n",ret); }
MANACHER---求最长回文串的更多相关文章
- Manacher算法 - 求最长回文串的利器
求最长回文串的利器 - Manacher算法 Manacher主要是用来求某个字符串的最长回文子串. 不要被manacher这个名字吓倒了,其实manacher算法很简单,也很容易理解,程序短,时间复 ...
- Manacher's Algorithm 马拉车算法(求最长回文串)
作用:求一个字符串中的最长子串,同时还可以求所有子串的长度. 题目链接: https://vjudge.net/contest/254692#problem/B 最长回文串长度的代码: int Man ...
- hdu 3068 最长回文 (Manacher算法求最长回文串)
参考博客:Manacher算法--O(n)回文子串算法 - xuanflyer - 博客频道 - CSDN.NET 从队友那里听来的一个算法,O(N)求得每个中心延伸的回文长度.这个算法好像比较偏门, ...
- hdu 3068 最长回文 【Manacher求最长回文子串,模板题】
欢迎关注__Xiong的博客: http://blog.csdn.net/acmore_xiong?viewmode=list 最长回文 ...
- Manacher(最长回文串)
http://acm.hdu.edu.cn/showproblem.php?pid=3068 最长回文 Problem Description 给出一个只由小写英文字符a,b,c...y,z组成的字符 ...
- Manacher算法,最长回文串
给你10000长度字符串,然你求最长回文字串,输出长度,暴力算法肯定超时 #include <iostream> #include <string> #include < ...
- Manacher 计算最长回文串
转自 http://blog.sina.com.cn/s/blog_3fe961ae0101iwc2.html 寻找字符串中的回文,有特定的算法来解决,也是本文的主题:Manacher算法,其时间复杂 ...
- Manacher 求最长回文子串算法
Manacher算法,是由一个叫Manacher的人在1975年发明的,可以在$O(n)$的时间复杂度里求出一个字符串中的最长回文子串. 例如这两个回文串“level”.“noon”,Manacher ...
- POJ 3376 Finding Palindromes(manacher求前后缀回文串+trie)
题目链接:http://poj.org/problem?id=3376 题目大意:给你n个字符串,这n个字符串可以两两组合形成n*n个字符串,求这些字符串中有几个是回文串. 解题思路:思路参考了这里: ...
- Manacher求最长回文
#1032 : 最长回文子串 时间限制:1000ms 单点时限:1000ms 内存限制:64MB 描写叙述 小Hi和小Ho是一对好朋友.出生在信息化社会的他们对编程产生了莫大的兴趣,他们约定好互相帮助 ...
随机推荐
- ASP.NET Web API上实现 Web Socket
1. 什么是Web Socket Web Socket是Html5中引入的通信机制,它为浏览器与后台服务器之间提供了基于TCP的全双工的通信通道.用以替代以往的LongPooling等comet st ...
- Linux 下查看文件字符编码和转换编码
Linux 下查看文件字符编码和转换编码 如果你需要在Linux中操作windows下的文件,那么你可能会经常遇到文件编码转换的问题.Windows中默认的文件格式是GBK(gb2312),而Linu ...
- poj 3273 Monthly Expense(贪心+二分)
题目:http://poj.org/problem?id=3273 题意:把n个数分成m份,使每份的和尽量小,输出最大的那一个的和. 思路:二分枚举最大的和,时间复杂度为O(nlog(sum-max) ...
- bzoj3926
题目的意思是叶子不超过20个……听说当初zjoi不少人被坑 分别对每个叶子以它为根dfs出20个dfs树,这样整个树的任何一个子串,都是某个dfs树上一个点到它的一个子孙的路径 每个dfs树,根到叶子 ...
- uva580Critical Mass
递推. 用f[i]代表i个盒子的放法,设g[i]=2^n-f[i],代表i个盒子不满足条件的放法. 枚举第一个U所在的位置j.则方法有g[j-2]*(2^(i-j-2))种,j-1必须是L. 所以 ...
- html之marquee详解[转]
该标签不是HTML3.2的一部分,并且只支持MSIE3以后内核,所以如果你使用非IE内核浏览器(如:Netscape)可能无法看到下面一些很有意思的效果该标签是个容器标签语法: <marquee ...
- textContent、innerText的用法,在文档中插入纯文本
有时候需要查询纯文本形式的元素内容,或者在文档中插入纯文本.标准的方法是用Node的textContent属性来实现: var para = document.getElementsByTagName ...
- SQL Server:把CSV文件导入到SQL Server表中
有时候我们可能会把CSV中的数据导入到某个数据库的表中,比如做报表分析的时候. 对于这个问题,我想一点也难不倒程序人员吧!但是要是SQL Server能够完成这个任务,岂不是更好! 对,SQL Ser ...
- 用户输入 i. 检测常用手势(一)
参考: http://blog.csdn.net/qq418716640/article/details/8508973http://www.cnblogs.com/mengdd/p/3335508. ...
- dos文件批量转换成unix文件
对于经常在windows环境下和linux环境同时使用的文件(如在windows系统下编写,在linux环境下编译的文件), 常常存在这样的问题:由于两种系统的格式文件格式不同,导致程序出现不期望的问 ...