题解-洛谷P5410 【模板】扩展 KMP(Z 函数)
题面
给定两个字符串 \(a,b\),要求出两个数组:\(b\) 的 \(z\) 函数数组 \(z\)、\(b\) 与 \(a\) 的每一个后缀的
LCP长度数组 \(p\)。
数据范围:\(1\le |a|,|b|\le 2\times 10^7\)。
蒟蒻语
别的题解为什么代码那么长、讲解那么复杂?蒟蒻不解,写篇易懂一点的,希望没有错误理解。
注意:蒟蒻的下标是从 \(0\) 开始的。
蒟蒻解
定义 \(z(i) (i>0)\):后缀 \(i\) 与字符串的 LCP 长度,劝退一点地说:
\]
对于求字符串 \(s\) 的 \(z\) 函数,可以用递推解决一部分问题,蒟蒻先放上精美的代码:
这里特定 \(z(0)=0\)(题目中 \(z(0)=|s|\))。
void getz(string s){
int l=0;
R(i,1,sz(s)){
if(l+z[l]>i) z[i]=min(z[i-l],l+z[l]-i);
while(i+z[i]<sz(s)&&s[z[i]]==s[i+z[i]]) z[i]++;
if(i+z[i]>l+z[l]) l=i;
}
// R(i,0,sz(s)) cout<<z[i]<<" ";cout<<'\n';
}
结论: 对于 \(i>0\),对任意 \(0\le l<i\) 都可以递推得:
\]
证明:
&s[(i)+(x)]\\
=&s[(l)+(i+x-l)]\\
=&s[(0)+(i+x-l)]\color{red}{(x\le l+z(l)-i)}\\
=&s[(i-l)+(x)]\\
=&s[(0)+(x)]\color{red}{(x\le z(i-l))}\\
\end{aligned}
\]
所以可以选定某个 \(0\le l<i\),初始化 \(z(i)=\min(z(i-l),l+z(l)-i)\),然后暴力判断字符相等增加 \(z(i)\)。
这里 \(l\) 选满足 \(j+z(j)(0\le j<i)\) 最大的 \(j\),这样每个字符只会被暴力判断一次,所以时间复杂度可以做到 \(\Theta(n)\)。
对于题目中的问题其实把 \(b\) 和 \(a\) 接起来做个 \(z\) 就可以了。
代码
#include <bits/stdc++.h>
using namespace std;
//Start
typedef long long ll;
typedef double db;
#define mp(a,b) make_pair((a),(b))
#define x first
#define y second
#define Be begin()
#define En end()
#define sz(a) int((a).size())
#define pb(a) push_back(a)
#define R(i,a,b) for(int i=(a),I=(b);i<I;i++)
#define L(i,a,b) for(int i=(b)-1,I=(a)-1;i>I;i--)
const int iinf=0x3f3f3f3f;
const ll linf=0x3f3f3f3f3f3f3f3f;
//Data
const int N=2e7;
ll ansz,ansp;
string a,b;
//Zfunction
int z[N<<1];
void getz(string s){
int l=0;
R(i,1,sz(s)){
if(l+z[l]>i) z[i]=min(z[i-l],l+z[l]-i);
while(i+z[i]<sz(s)&&s[z[i]]==s[i+z[i]]) z[i]++;
if(i+z[i]>l+z[l]) l=i;
}
// R(i,0,sz(s)) cout<<z[i]<<" ";cout<<'\n';
}
//Main
int main(){
ios::sync_with_stdio(0);
cin.tie(0),cout.tie(0);
cin>>a>>b,getz(b+a);
ansz^=1ll*(sz(b)+1)*(0+1);
R(i,1,sz(b)) ansz^=1ll*(min(z[i],sz(b)-i)+1)*(i+1);
R(i,0,sz(a)) ansp^=1ll*(min(z[i+sz(b)],sz(b))+1)*(i+1);
cout<<ansz<<'\n'<<ansp<<'\n';
return 0;
}
祝大家学习愉快!
题解-洛谷P5410 【模板】扩展 KMP(Z 函数)的更多相关文章
- luogu P5410 模板 扩展 KMP Z函数 模板
LINK:P5410 模板 扩展 KMP Z 函数 画了10min学习了一下. 不算很难 思想就是利用前面的最长匹配来更新后面的东西. 复杂度是线性的 如果不要求线性可能直接上SA更舒服一点? 不管了 ...
- [洛谷P4720] [模板] 扩展卢卡斯
题目传送门 求组合数的时候,如果模数p是质数,可以用卢卡斯定理解决. 但是卢卡斯定理仅仅适用于p是质数的情况. 当p不是质数的时候,我们就需要用扩展卢卡斯求解. 实际上,扩展卢卡斯=快速幂+快速乘+e ...
- [洛谷P4777] [模板] 扩展中国剩余定理
扩展中国剩余定理,EXCRT. 题目传送门 重温一下中国剩余定理. 中国剩余定理常被用来解线性同余方程组: x≡a[1] (mod m[1]) x≡a[2] (mod m[2]) ...... x≡a ...
- 洛谷P3373 [模板]线段树 2(区间增减.乘 区间求和)
To 洛谷.3373 [模板]线段树2 题目描述 如题,已知一个数列,你需要进行下面两种操作: 1.将某区间每一个数加上x 2.将某区间每一个数乘上x 3.求出某区间每一个数的和 输入输出格式 输入格 ...
- 题解-洛谷P4724 【模板】三维凸包
洛谷P4724 [模板]三维凸包 给出空间中 \(n\) 个点 \(p_i\),求凸包表面积. 数据范围:\(1\le n\le 2000\). 这篇题解因为是世界上最逊的人写的,所以也会有求凸包体积 ...
- 洛谷P3375 [模板]KMP字符串匹配
To 洛谷.3375 KMP字符串匹配 题目描述 如题,给出两个字符串s1和s2,其中s2为s1的子串,求出s2在s1中所有出现的位置. 为了减少骗分的情况,接下来还要输出子串的前缀数组next.如果 ...
- LCT总结——概念篇+洛谷P3690[模板]Link Cut Tree(动态树)(LCT,Splay)
为了优化体验(其实是强迫症),蒟蒻把总结拆成了两篇,方便不同学习阶段的Dalao们切换. LCT总结--应用篇戳这里 概念.性质简述 首先介绍一下链剖分的概念(感谢laofu的讲课) 链剖分,是指一类 ...
- 【AC自动机】洛谷三道模板题
[题目链接] https://www.luogu.org/problem/P3808 [题意] 给定n个模式串和1个文本串,求有多少个模式串在文本串里出现过. [题解] 不再介绍基础知识了,就是裸的模 ...
- 题解-洛谷P6788 「EZEC-3」四月樱花
题面 洛谷P6788 「EZEC-3」四月樱花 给定 \(n,p\),求: \[ans=\left(\prod_{x=1}^n\prod_{y|x}\frac{y^{d(y)}}{\prod_{z|y ...
随机推荐
- select的限制
/*一.select实现并发服务器并发的两点限制 1.一个进能够打开的最大文件描述符限制.可以通过两种方式修改 ulimit -n :获取最大文件描述符个数 ulimit -n 2048:修改为204 ...
- 年轻人不讲武德来白piao我这个老同志
朋友们好啊,我是码农小胖哥. 今天有个同学问我在吗,我说什么事? 给我发个截图,我一看!噢,原来是帮忙搞个定时任务,还是动态的. 他说了两种选择,一种是用DelayQueue,一种是用消息队列. 他说 ...
- wireguard使用
1.编译与安装 sudo apt-get install libmnl-dev libelf-dev linux-headers-$(uname -r) build-essential pkg-con ...
- mysql开发常用技巧总结
1.查询某个schema,某张表的创建时间. SELECT CREATE_TIME FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA='db_camp ...
- 灵活运用的@RequestParam和@RequestBody
最近在编写项目的过程中,老出现前后端传递参数格式不一致.不统一的问题,对于一个已经快工作一年的Java程序员来说,实属不合格,所以我就下来好好研究了一下@RequestParam和@RequestBo ...
- K8S环境的Jenkin性能问题描述
Return Homezq2599 CnBlogsHomeContactAdminPosts - 75 Articles - 0 Comments - 16 K8S环境的Jenkin性能问题处理 环境 ...
- VulnHub靶场学习_HA:Forensics
HA:Forensics Vulnhub靶场 下载地址:https://www.vulnhub.com/entry/ha-forensics,570/ 背景: HA: Forensics is an ...
- 纯干货分享!2020阿里java岗笔试面试题总结(附答案)
前言 2020金九银十马上结束,现为大家整理了这次金九银十面试阿里的面试题总结,都是我从朋友那拿到的面试真题,话不多说,满满的干货分享给大家! int a=10是原子操作吗? 是的. 注意点: i+ ...
- 工作一年半被裁掉,机缘巧合拿到阿里P7offer,得亏我看过这份“突击”面试宝典
前言 不论是校招还是社招都避免不了各种⾯试.笔试,如何去准备这些东⻄就显得格外重要.不论是笔试还是⾯试都是有章可循的,我这个"有章可循"说的意思只是说应对技术⾯试是可以提前准备,所 ...
- 手把手教你用思维导图软件iMindMap制作计划表
在日常生活中小编也经常使用思维导图软件iMindMap来创建思维导图以规划工作及学习的安排.尤其是时间安排类型的思维导图,能极大程度的节约我们的时间,接下来就由小编以自己假期的社会实践向大家分享一下怎 ...