博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Palindrome Partition CodeForces - 932G 回文树+DP+(回文后缀的等差性质)
阅读量:5030 次
发布时间:2019-06-12

本文共 1437 字,大约阅读时间需要 4 分钟。

题意:

给出一个长度为偶数的字符串S,要求把S分成k部分,其中k为任意偶数,设为a[1..k],且满足对于任意的i,有a[i]=a[k-i+1]。问划分的方案数。 

n<=1000000

 

题解:

反正我是不会做   (我是转载的yyb博客,巨佬写的超级超级)

基本就是照着laofulaofu的打了一遍(laofu太强啦)

这题分成了两个步骤

如果直接分kk段我们是没法直接判断的
假设两段si,ski+1
因为si=ski+1=x1x2.....xj  
假设si的开始位置为p
假设原串S的长度为n
si=S[p]S[p+1]....S[p+j1]
ski+1=S[njp+1]S[njp+2]...
对应相等的关系是
S[p]=S[npj+1]
如果p=1考虑一下特殊情况
那么就是S[1]=S[nj]
那么,如果我们有一个串S
S=S[1]S[n]S[2]S[n2].....
那么,对应到上面的相等关系里面,
就是S[1..j]是一个回文串
其他的每一组对应关系也是如此
所以题目转换成了:
告诉你了S回答把S分为若干个长度为偶数的回文串的方案数
(如果没有搞清楚可以手玩一下)

这个就是一个裸的dp

f[i]f[i]表示S[1..i]S′[1..i]划分为若干长度为偶数的回文串的方案数
得到转移方程:

f[i]=jf[j1]

其中,S[j,i]S′[j,i]是回文串
那么,每一个jj对应的位置相当于是S[1..i]S′[1..i]的回文后缀
构建出回文树之后沿着lastfail就可以得到所有的j的位置

 

这样子的复杂度是O(回文串数量)的,显然会超时,考虑如何优化。 

有一个小结论就是一个回文串S的一个后缀T是回文串当且仅当T是S的border。 
有一个性质就是一个串的所有border可以划分成O(log)段等差数列。 

维护pre[p]表示节点p下一个等差数列的末项。 d[p]表示公差

 

1 #include 
2 #include
3 #include
4 #include
5 #include
6 #include
7 #include
8 #include
9 #include
10 #include
11 #include
12 #include
13 #include
14 15 #define pi acos(-1.0) 16 #define eps 1e-9 17 #define fi first 18 #define se second 19 #define rtl rt<<1 20 #define rtr rt<<1|1 21 #define bug printf("******\n") 22 #define mem(a, b) memset(a,b,sizeof(a)) 23 #define name2str(x) #x 24 #define fuck(x) cout<<#x" = "<
<
View Code

 

转载于:https://www.cnblogs.com/qldabiaoge/p/11403862.html

你可能感兴趣的文章
20170605
查看>>
github自己用--(未完)
查看>>
软件测试工程师的技能树
查看>>
理解OAuth 2.0授权
查看>>
HTTP状态码整理
查看>>
回调函数
查看>>
快速检测一个点是否包含在一个2d三角形内
查看>>
linux系统rpm和yum软件包管理
查看>>
HDU 5590 ZYB's Biology 水题
查看>>
Codeforces Round #296 (Div. 1) B. Clique Problem 贪心
查看>>
HDU 5115 Dire Wolf 区间dp
查看>>
Codeforces Round #332 (Div. 2) D. Spongebob and Squares 数学题枚举
查看>>
解决SWFUpload在Chrome、Firefox等浏览器下的问题
查看>>
Linux脚本入门(1)
查看>>
HCatalog
查看>>
Java:创建线程
查看>>
Java: 面向对象程序设计(下)
查看>>
java小练习
查看>>
bsxfun: normalizing many vectors
查看>>
深入理解Java中的final关键字
查看>>