【知识点】Manacher算法详解
Manacher算法
算法简介
算法,即“马拉车”算法,是一种高效()的求最长回文子串的算法。相比于 , 也许更好理解一些。
算法原理
对于传统的暴力解法,求最长回文子串的方式应该是对于每个位置 ,向两边“扩大”以寻找回文子串,再记录答案。易证,此解法时间复杂度为 。
众所周知,每一个毒瘤算法都有一个暴力的开头。
算法首先要对原字符串进行处理。因为回文串分为两种,“奇回文”和“偶回文”:
"abcba"
"abba"
首先,在每两个字符之间放入一个没有出现在原串的字符,如 ;接着,将字符串的两边插入另外两个不同的,且没有出现在原串的字符,如 和 。操作结果如下:
"@a#b#b#a$"
"@a#b#c#b#a$"
神奇的事情发生了,“奇回文”和“偶回文”都转化成了“奇回文”。同时,在判定回文串的过程中也不用判边界了,因为修改后字符串边界字符不一样。
除此之外, 算法还引入了一个数组 , 表示以位置 为中心的“最长回文半径”。对于字符串 如表所示:
0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
@ | # | a | # | b | # | b | # | a | # | d | # | c | # | a | # | c | # | d | # | a | # | $ | |
1 | 1 | 2 | 1 | 2 | 3 | 2 | 1 | 2 | 1 | 2 | 1 | 2 | 1 | 6 | 1 | 2 | 1 | 2 | 1 | 2 | 1 | 1 |
显然,最终答案就是 。那么 算法就讲完了……等等, 数组怎么求?
算法过程
首先,看下图:
引入两个变量, 和 , 表示以 为中心点的最大回文子串右边界。
假设现在要求 ,那么就有:
if(i<mx) p[i]=min(p[id*2-i],mx-i);
这样就可以加快速度。但是……为什么?为什么为什么???
设 ,也就是说, 是 关于 的对称点。因为是从前往后循环, 是已知的。下面开始分类讨论:
- 若 ,可得以 为中心,以 的对称点 到 的距离为半径形成的回文字符串是存在的,并且 到 与 到 一一对应,所以 是 目前可以更新到的最大回文半径;
- 若 ,也就是 的回文半径小于 到 的距离,可得 。
于是就有了你看到的反人类代码。
完整代码
int manacher(string &s_src) { /* * @params s_src为源字符串,s为预处理后的字符串 */ string s="@"; for(auto &ch: s_src) { s.push_back('#'); s.push_back(ch); } s+="#$"; int id,mx=0,res=0; for(int i=1;i<s.size()-1;i++) { if(i<=mx) p[i]=min(p[id*2-i],mx-i); while(s[i-p[i]]==s[i+p[i]]) p[i]++; if(i+p[i]>mx) id=i,mx=i+p[i]-1; res=max(res,p[i]-1); } return res; }
本文作者:ExplodingKonjac
本文链接:https://www.cnblogs.com/ExplodingKonjac/p/13561740.html
版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。
【推荐】还在用 ECharts 开发大屏?试试这款永久免费的开源 BI 工具!
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· .NET 原生驾驭 AI 新基建实战系列:向量数据库的应用与畅想
· 从问题排查到源码分析:ActiveMQ消费端频繁日志刷屏的秘密
· 一次Java后端服务间歇性响应慢的问题排查记录
· dotnet 源代码生成器分析器入门
· ASP.NET Core 模型验证消息的本地化新姿势
· 开发的设计和重构,为开发效率服务
· 从零开始开发一个 MCP Server!
· Ai满嘴顺口溜,想考研?浪费我几个小时
· 从问题排查到源码分析:ActiveMQ消费端频繁日志刷屏的秘密
· .NET 原生驾驭 AI 新基建实战系列(一):向量数据库的应用与畅想