首页 > 其他分享 >Manacher 学习笔记

Manacher 学习笔记

时间:2025-01-04 18:22:22浏览次数:1  
标签:奇数 Manacher 笔记 times 学习 数组 长度 回文

\(\text{Manacher 学习笔记}\)

一、引入

首先我们需要知道的是 \(\text{Manacher}\) 是解决回文串问题的有效工具。

一个通用的问题模型是给定一个长度为 \(n\) 的字符串 \(s\),统计该字符串中所有的回文子串的个数。\(\text{Manacher}\) 算法可以在 \(O(n)\) 的时间复杂度内解决这个问题。

我们知道的是,对于任意一个回文串 \(s[i,j]\),有对称中心 \(\lfloor \dfrac{i+j-1}{2}\rfloor\)。考虑到奇数和偶数长度回文串的差异,我们用两个数组 \(d_1(i),d_2(i)\) 分别表示长度为奇数、偶数的回文串中心为 \(i\) 时回文串的个数。

现在我们的问题就是快速求出 \(d_1,d_2\) 两个数组。

二、算法

我们先考虑 \(d_1\) 的求解过程,求出 \(d_1\) 数组的基本思想是采用之前维护过的 \(d_1\) 数组信息来更新现有的 \(d_1\) 数组。为了叙述方便,下文以 \(d\) 数组代指 \(d_1\) 数组。

既然这样,在求 \(d(i)\) 时我们需要维护 \([1,i-1]\) 范围内边界最靠右的回文串的边界 \(l,r\),初始设 \(l=1,r=0\)。

现在考虑计算 \(d(i)\) 的方式:

  • 若 \(i>r\),暴力匹配;
  • 若 \(i\le r\):

由于 \([l,r]\) 是回文串,那么 \(d(i)=d(l+r-i)\),也就是将中心为 \(l+r-i\) 为中心的回文串 copy 到了 \(i\) 上。然而需要留意的是,我们只能保证在 \([l,r]\) 内的部分是回文串,而这个部份内回文串的最大长度显然是 \(r-i+1\)。

考虑复杂度分析:\(r\) 是单调递增的,而暴力算法运行一次一定会使得 \(r\) 增长 \(1\),因此复杂度为 \(O(n)\)。

现在考虑 \(d_2(i)\) 的求解——但其实我们有更好的方法用一套模板解决两个问题。

考虑在原字符串每个字符的两侧都插入一个其它字符,这样一来所有回文串都可以归约到奇数串的情况,例如 aba \(\to\) a#b#aabba \(\to\) a#b#b#a。对于多统计的情形,容易得到关系 \(d(i)=2\times d_1(i)=2\times d_2(i)+1\)。

给出代码:

void manacher() {
	int l = 1, r = 0;
	for (int i = 1; i <= n; i++) {
		int k = (i > r) ? 0 : min(d[l + r - i], r - i + 1);
		while (i + k <= n && i - k >= 1 && equ(s[i - k], s[i + k])) ++k;
		d[i] = k--;
		if (i + k > r) l = i - k, r = i + k;
	}
}

三、应用

应用典型是求最长回文子串。对于长度为奇数的回文串,最长的长度是 \(2\times d_1-1=d-1\),偶数是 \(2\times d_2=d-1\)。于是返回 \(\max_d-1\) 即可。

标签:奇数,Manacher,笔记,times,学习,数组,长度,回文
From: https://www.cnblogs.com/Rock-N-Roll/p/18652234

相关文章

  • 03专升本数据结构笔记 第三章:栈和队列
    专升本数据结构笔记第三章:栈和队列阿洛学长笔记lovettz栈和队列任务一栈的定义、存储结构和基本操作(阿洛学长)一、栈的定义及其基本操作二、栈的顺序存储结构三、栈的链式存储结构四、栈在递归中的应用一、栈的定义及其基本操作1.栈的定义栈是一种只允许在表的......
  • 02专升本数据结构笔记 第二章:线性表
    专升本数据结构笔记第二章:线性表阿洛学长笔记lovettz线性表任务一线性表的定义和基本操作(阿洛学长)一、线性表的定义线性表是由n(n≥0)个类型相同的数据元素a1,a2,…,an组成的有限序列,数据元素之间是一对一的关系,记作L=(a1,a2,…,ai-1,ai,ai+1,…,an)(由n(n≥0)个......
  • 学习-Nginx-安装nginx1.21.6开源软件
    下载地址http://nginx.org/download/nginx-1.21.6.tar.gz通过网盘分享的文件:Nginx1.21.6链接:https://pan.baidu.com/s/1tcsTs2IEmN80wt5VQ5U3PA?pwd=sky1提取码:sky1Xftp传输安装包解压缩安装包tarzxvfnginx-1.21.6进入到nginx文件夹查看需要的依赖./configu......
  • 学习-Niginx-执行yum install -y gcc时候报错“14: curl#6 - "Could not resolve host
    报错信息如下:[root@localhostnginx-1.21.6]#yuminstall-ygcc已加载插件:fastestmirrorLoadingmirrorspeedsfromcachedhostfileCouldnotretrievemirrorlisthttp://mirrorlist.centos.org/?release=7&arch=x86_64&repo=os&infra=stockerrorwas14:curl#6......
  • 【强化学习】Double DQN(Double Deep Q-Network)算法
            ......
  • 【强化学习】双延迟深度确定性策略梯度算法(TD3)详解
            ......
  • 素数入门笔记
    试除法从\(2\)枚举到\(\lfloor\sqrtn\rfloor\)判断能否整除。朴素筛法从小到大枚举每个数,将范围内它的倍数全部标记为合数。时间复杂度显然就是调和级数\(O(n\logn)\)。埃氏筛观察到一个合数必定可以通过某个质数乘上某个数得到。从小到大枚举每个质数,将范围内它的......
  • 学期(如2024-2025-1) 学号(如:20241300) 《计算机基础与程序设计》第X周学习总结
    20241303《计算机基础与程序设计》课程总结一.(按顺序)每周作业链接汇总第一周作业1.简要内容:①课程概论②工业革命与浪潮之巅③信息与信息安全④计算机系统概论⑤计算机安全⑥计算的限制⑦计算思维2.二维码第二周作业1.简要内容:①数字化②信息安全2.二维码第三周作业......
  • 在学习python的过程中什么最难?
    在学习Python的过程中,不同的人会遇到不同的挑战,具体的难点取决于你的背景知识、学习目标和编程经验。以下是一些常见的难点和应对建议:1.理解编程基础概念如果你是编程新手,以下概念可能会让人困惑:变量和数据类型:例如何时用字符串(str)、整数(int)或列表(list)。条件语句和循环:if......
  • 怎么开始学习python?纯小白
    学习Python是一项很有价值的技能,无论您是初学者,还是希望提升自己编程能力的人。Python具有简洁易懂的语法,广泛应用于数据科学、网络开发、人工智能等多个领域。下面是一个适合初学者的学习路线图,可以帮助您高效开始学习Python:1. 基础知识学习学习目标:理解Python的基本语法和......