正题

题目链接:https://www.luogu.com.cn/problem/CF932G


题目大意

给出一个长度为nnn的字符串,将其分为kkk段(kkk为任意偶数),记为ppp。要求满足对于任意iii都有pi=pk−i+1p_i=p_{k-i+1}pi​=pk−i+1​。求方案数。

1≤n≤1061\leq n\leq 10^61≤n≤106


解题思路

考虑将字符串化为S1SnS2Sn−1S3Sn−2...S_1S_nS_2S_{n-1}S_3S_{n-2}...S1​Sn​S2​Sn−1​S3​Sn−2​...这样的形式,可以发现对于原本相同的段在这里就被表示为了一个偶回文子串。

那么问题就变为了划分若干个偶回文子串。设fif_ifi​表示前iii个的方案的话有一种比较简单的做法,建立PAMPAMPAM后求出每个前缀的所有偶回文后缀,然后暴力转移。

但是这样的是O(n2)O(n^2)O(n2)的,时间复杂度不符合要求,考虑优化。对于一个回文串来说它的所有回文后缀就是它的borderborderborder。而broderbroderbroder有一个性质就是所有broderbroderbroder的长度可以被划分成logloglog个等差数列。

我们可以在PAMPAMPAM上维护这些等差数列,记录topitop_itopi​表示节点iii所在的等差数列的顶部,然后每次使用toptoptop往上跳。加入新的xxx节点(或者覆盖以前的已经有的节点)的时候累计一下自己作为末尾时所在等差数列方案和就好了

时间复杂度O(nlog⁡n)O(n\log n)O(nlogn)


code

#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int N=1e6+10,P=1e9+7;
int n,cnt,pos[N],len[N],dis[N],fa[N],top[N],ch[N][26];
char t[N],s[N];int f[N],g[N];
int jump(int x,int p){while(s[p-len[x]-1]!=s[p])x=fa[x];return x;
}
int Insert(int x,int p){x=jump(x,p);int c=s[p]-'a';if(!ch[x][c]){++cnt;len[cnt]=len[x]+2; int y=jump(fa[x],p);fa[cnt]=ch[y][c];y=cnt;dis[y]=len[y]-len[fa[y]];if(dis[y]!=dis[fa[y]])top[y]=y;else top[y]=top[fa[y]];ch[x][c]=y;}return ch[x][c];
}
int main()
{scanf("%s",t+1);n=strlen(t+1);if(n&1)return puts("0")&0;for(int i=1;i<=n;i+=2)s[i]=t[i/2+1];for(int i=2;i<=n;i+=2)s[i]=t[n-i/2+1];len[1]=-1;fa[0]=top[1]=cnt=1;for(int i=1;i<=n;i++)pos[i]=Insert(pos[i-1],i);f[0]=1;for(int i=1;i<=n;i++){for(int x=pos[i];x;x=fa[top[x]]){g[x]=f[i-len[top[x]]];if(x!=top[x])(g[x]+=g[fa[x]])%=P;if(!(i&1))(f[i]+=g[x])%=P;}}printf("%d\n",f[n]);return 0;
}

CF932G-Palindrome Partition【PAM】相关推荐

  1. Uva - 12050 Palindrome Numbers【数论】

    题目链接:uva 12050 - Palindrome Numbers 题意:求第n个回文串 思路:首先可以知道的是长度为k的回文串个数有9*10^(k-1),那么依次计算,得出n是长度为多少的串,然 ...

  2. CF932G Palindrome Partition

    思路 首先把字符串变为\(S[1]S[n]s[2]s[n-1] \dots\) 这样原来的一个合法的划分方案就变成了用k个长度为偶数的回文子串划分的方案, 然后直接DP,对i位置,可转移的位置就是它的 ...

  3. P3649-[APIO2014]回文串【PAM】

    正题 题目链接:https://www.luogu.com.cn/problem/P3649 题目大意 一个字符串,求最大的回文串长度×出现次数 解题思路 构建出PAM\text{PAM}PAM然后统 ...

  4. linux系统pam配置文件,【PAM】 How to Configure and Use PAM in Linux?

    一.什么是PAM PAM(Pluggable Authentication Modules )是由Sun提出的一种认证机制. 它通过提供一些动态链接库和一套统一的API,将系统提供的服务 和该服务的认 ...

  5. P4287-[SHOI2011]双倍回文【PAM】

    正题 题目链接:https://www.luogu.com.cn/problem/P4287 题目大意 长度为nnn的字符串.定义wRw^RwR表示字符串www的翻转. 一个双倍回文可以表示为wwRw ...

  6. P5496-[模板]回文自动机【PAM】

    正题 题目链接:https://www.luogu.com.cn/problem/P5496 题目大意 长度为nnn的字符串,求每个字符串作为结尾有多少个回文串. 解题思路 PAMPAMPAM. 下面 ...

  7. Spark _10_补充部分算子【三】

    补充算子 transformations mapPartitionWithIndex 类似于mapPartitions,除此之外还会携带分区的索引值. repartition 增加或减少分区.会产生s ...

  8. 【LeetCode】Palindrome Partitioning 解题报告

    [题目] Given a string s, partition s such that every substring of the partition is a palindrome. Retur ...

  9. 【leetcode】132. Palindrome Partitioning II

    题目如下: 解题思路:本题是[leetcode]131. Palindrome Partitioning的升级版,要求的是求出最小cuts,如果用[leetcode]131. Palindrome P ...

最新文章

  1. Go语言学习(七)-----练练笔之递归
  2. 集成学习(西瓜书学习)
  3. jenkins 手动执行_Jenkins Git client插件命令执行漏洞(CVE201910392)
  4. h.264 视频解码的一点小经验
  5. 高并发系统数据幂等性
  6. 图解50道sql编写题
  7. JS中Ajax的方法和应用
  8. fiddler抓包教程
  9. 如何使用免费的WordPress FooGallery插件创建图像库
  10. 企业电子邮箱的地址格式
  11. matlab:pause命令
  12. 如何删除tmp计算机桌面,win10系统下tmp临时文件删除不了像何解决
  13. 找出成绩全及格的学生(python)实现
  14. Vue+Webpack打造todo应用(慕课学习笔记)
  15. 参赛邀请 | 第二届古汉语自动分析国际评测EvaHan(古汉语机器翻译)开始报名...
  16. 新月,上弦月,满月,下弦月的区别
  17. 独家 | 揭底!BiYong被爆严重用户隐私安全漏洞!
  18. 如何在显示图片缩略图时不挤压拉伸图片
  19. 人生若只如初见-纳兰性德
  20. GUIBuilder 5.36_万向钱潮2019年盈利5.36亿元下滑25.82% 车产销下降

热门文章

  1. docker 修改阿里镜像源_Jetson Nano 修改源镜像
  2. 与ln的指数转化公式_高考数学48条秒杀型公式与方法
  3. 数字转字符函数_Excel之文本函数CONCATENATE/TEXT/LEFT/MID/RIGHT/FIND/LEN
  4. java thread join()_Java Thread join() 的用法
  5. java 接口的静态方法_Java8新特性:接口的默认方法与接口的静态方法
  6. 如何在mysql中打开mongodb_图解:如何从MySQL移植到MongoDB
  7. 模拟时钟中断的产生及设计一个对时钟中断事件进行处理的模拟程序_操作系统基础6-支持操作系统的最基本的硬件-中断...
  8. android平板 useragent,移动端适配 user-Agent
  9. java 变成题_Java 习题8 参考答案及解析
  10. [Java基础]字节缓冲流