CF932G Palindrome Partition(回文自动机)
CF932G Palindrome Partition(回文自动机)
题解时间
首先将字符串 $ s[1...n] $ 变成 $ s[1]s[n]s[2]s[n-1]... $
就变成了求将字符串全部划分为偶回文串的方案数。
建回文树大力跳$ fail $ 直接 $ dp $ 的复杂度是十分优秀的 $ O ( n ^ {2} ) $。
优化不容易想到。
考虑字符串上第 $ j $ 位为结尾的所有回文子串,毫无疑问它们在树上是一条链。
但它有个更重要的性质。
其中所有长度 $ > j / 2 $ 的子串的 $ len $ 等差。
证明有点难,但这个结论可能对做过[WC2016]论战捆竹竿的人来说十分熟悉。
然后将等差段的dp值整合到一起,每次跳就是 $ O( log_{2} n ) $。
然后就可以做了。
#include<bits/stdc++.h>
using namespace std;
typedef long long lint;
struct pat{int x,y;pat(int x=0,int y=0):x(x),y(y){}bool operator<(const pat &p)const{return x==p.x?y<p.y:x<p.x;}};
template<typename TP>inline void read(TP &tar)
{
	TP ret=0,f=1;char ch=getchar();
	while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
	while(ch>='0'&&ch<='9'){ret=ret*10+(ch-'0');ch=getchar();}
	tar=ret*f;
}
namespace RKK
{
const int N=1000011,mo=1000000007;
void doadd(int &a,int b){if((a+=b)>=mo) a-=mo;}
int dlen[N],anc[N];
struct remilia{int tranc[26],len,fail;};
struct sakuya
{
	remilia p[N];
	int tcnt,fin;
	void init()
	{
		tcnt=fin=1;
		p[0].len=0,p[1].len=-1;
		p[0].fail=p[1].fail=1;
		anc[0]=1;
	}
	sakuya(){init();}
	int match(char *s,int i,int px){return s[i-p[px].len-1]==s[i];}
	void ins(char *s,int i)
	{
		int ch=s[i]-'a';
		int npx,lpx,lpy;
		lpx=fin;
		while(!match(s,i,lpx)) lpx=p[lpx].fail;
		if(!p[lpx].tranc[ch])
		{
			npx=++tcnt,p[npx].len=p[lpx].len+2;
			lpy=p[lpx].fail;
			while(!match(s,i,lpy)) lpy=p[lpy].fail;
			p[npx].fail=p[lpy].tranc[ch];
			p[lpx].tranc[ch]=npx;
			dlen[npx]=p[npx].len-p[p[npx].fail].len;
			anc[npx]=p[npx].fail;if(dlen[npx]==dlen[p[npx].fail]) anc[npx]=anc[p[npx].fail];
		}
		fin=p[lpx].tranc[ch];
	}
}pam;
int n;char str[N],rts[N];
int dp[N],dg[N];
int main()
{
	#ifdef RDEBUG
	freopen("sample.in","r",stdin);
	#endif
	scanf("%s",str+1),n=strlen(str+1);
	for(int i=1;i<=n>>1;i++) rts[(i<<1)-1]=str[i];
	reverse(str+1,str+1+n);
	for(int i=1;i<=n>>1;i++) rts[i<<1]=str[i];
	dg[0]=1;
	for(int i=1;i<=n;i++)
	{
		pam.ins(rts,i);for(int px=pam.fin;px;px=anc[px])
		{
			dp[px]=dg[i-pam.p[anc[px]].len-dlen[px]];
			if(anc[px]!=pam.p[px].fail) doadd(dp[px],dp[pam.p[px].fail]);
			if((i&1)==0) doadd(dg[i],dp[px]);
		}
	}
	printf("%d\n",dg[n]);
	return 0;
}
}
int main(){return RKK::main();}
												
											CF932G Palindrome Partition(回文自动机)的更多相关文章
- 【CF932G】Palindrome Partition 回文自动机
		
[CF932G]Palindrome Partition 题意:给你一个字符串s,问你有多少种方式,可以将s分割成k个子串,设k个子串是$x_1x_2...x_k$,满足$x_1=x_k,x_2=x_ ...
 - [2019杭电多校第二场][hdu6599]I Love Palindrome String(回文自动机&&hash)
		
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6599 题目大意为求字符串S有多少个子串S[l,r]满足回文串的定义,并且S[l,(l+r)/2]也满足 ...
 - 2019牛客暑期多校训练营(第六场)C - Palindrome Mouse (回文自动机)
		
https://ac.nowcoder.com/acm/contest/886/C 题意: 给出一个串A , 集合S里面为A串的回文字串 , 现在在集合S里面找出多少对(a,b),b为a的字串 分析: ...
 - hdu多校第二场1009 (hdu6599) I Love Palindrome String 回文自动机/字符串hash
		
题意: 找出这样的回文子串的个数:它本身是一个回文串,它的前一半也是一个回文串 输出格式要求输出l个数字,分别代表长度为1~l的这样的回文串的个数 题解: (回文自动机和回文树是一个东西) 首先用回文 ...
 - Codeforces 932G Palindrome Partition - 回文树 - 动态规划
		
题目传送门 通往???的传送点 通往神秘地带的传送点 通往未知地带的传送点 题目大意 给定一个串$s$,要求将$s$划分为$t_{1}t_{2}\cdots t_{k}$,其中$2\mid k$,且$ ...
 - Codeforces 932G Palindrome Partition 回文树+DP
		
题意:给定一个串,把串分为偶数段 假设分为$s_1,s_2,s_3....s_k$ 求满足$ s_1=s_k,s_2=s_{ k-1 }... $的方案数模$10^9+7$ $|S|\leq 10^6 ...
 - 2019 Multi-University Training Contest 2  I.I Love Palindrome String(回文自动机+字符串hash)
		
Problem Description You are given a string S=s1s2..s|S| containing only lowercase English letters. F ...
 - WHU 583 Palindrome ( 回文自动机 && 本质不同的回文串的个数 )
		
题目链接 题意 : 给你一个串.要你将其划分成两个串.使得左边的串的本质不同回文子串的个数是右边串的两倍.对于每一个这样子的划分.其对答案的贡献就是左边串的长度.现在要你找出所有这样子的划分.并将贡献 ...
 - HDU-6599  I Love Palindrome String(回文自动机+字符串hash)
		
题目链接 题意:给定一个字符串\(|S|\le 3\times 10^5\) 对于每个 \(i\in [1,|S|]\) 求有多少子串\(s_ls_{l+1}\cdots s_r\)满足下面条件 \( ...
 
随机推荐
- Mapper代理方式
			
MyBatis入门初体验时,使用mapper的方式: 很奇怪,为什么只有interface二没有实现,怎么就可以从数据库中查出准确的数据.其实Mybatis利用了JDK动态代理实现了相应功能,下面详细 ...
 - 【C# IO 操作 】详解去掉字符顺序标记(BOM)头的方法
			
类似WINDOWS自带的记事本等软件,在保存一个以UTF-8编码的文件时,会在文件开始的地方插入三个不可见的字符(0xEF 0xBB 0xBF,即BOM).它是一串隐藏的字符,用于让记事本等编辑器识别 ...
 - C#析构函数(方法)
			
析构方法是在垃圾回收.释放资源时使用的.析构函数用于析构类的实例.备注: 不能在结构中定义析构函数.只能对类使用析构函数. 一个类只能有一个析构函数. 无法继承或重载析构函数. ...
 - 截图工具snipaste
			
下载地址: https://zh.snipaste.com/download.html 使用: 按F1截图,截图后按F3悬浮
 - .net mvc项目本地调试:浏览器一直转圈无法访问
			
原因: 通过 bundles.Add 方式給多个 js文件添加 匿名,再通过 @Scripts.Render 引入的时候, js 里面使用了 const 来定义变量,就会导致访问pending,具体 ...
 - 数仓建模—ID Mapping
			
早晨起床的时候,发现自己尿分叉,我没有多想,简单洗洗就匆忙出门.路过早餐店,我看到师傅熟练的拉扯一小块面团,拉至细长条,然后放入油锅中,不一会功夫,一根屎黄色的油条便出锅了,卖相不错.我在想,小到炸屎 ...
 - CAS单点登录(一)——初识SSO
			
转载:https://blog.csdn.net/Anumbrella/article/details/80821486 一.初识CAS 首先我们来说一下CAS,CAS全称为Central Authe ...
 - selenium+python自动化105 - selenium 如何在已打开的浏览器上继续运行自动化脚本?
			
前言 使用selenium 做web自动化的时候,经常会遇到这样一种需求,是否可以在已经打开的浏览器基础上继续运行自动化脚本? 这样前面的验证码登录可以手工点过去,后面页面使用脚本继续执行,这样可以解 ...
 - Pandas:plot相关函数
			
0.注意事项 及 各种错误 1)绘制bar图时,如果出现重复的x值被合并到一个情况(导致X轴应该显示内容有缺失),可能是由于Pandas版本太低: 2)无法设置中文title,在代码中加入两句话: p ...
 - Windows Service 安装、启动和卸载
			
win+R输入cmd,以管理员身份运行cmd: 安装: 1.cd C:\Windows\Microsoft.NET\Framework\v4.0.30319 回车 2.输入(InstallUtil ...