传送门


先不考虑”不是连续的一段“这一个约束条件。可以知道:第$i$位与第$j$位相同,可以对第$\frac{i+j}{2}$位置上产生$1$的贡献(如果$i+j$为奇数表明它会对一条缝产生$1$的贡献),而每一个位置上或缝上的满足条件的字符串的个数就是$2^\text{贡献}-1$。把$\frac{1}{2}$忽略掉,也就是说:第$i$位与第$j$位相同时会在第$i+j$位产生$1$的贡献。这个是经典的生成函数+$FFT$求解的问题。具体来说,将$a,b$两个字母分开计算,以计算$a$的贡献为例,如果第$i$位上为$a$,则两个多项式的$x^i$项的系数为$1$,否则为$0$,然后将两个多项式做卷积得到的结果的每一项的系数就是$a$字母对每一位做的贡献,$b$同理。

然后我们考虑减掉连续的一段。连续的一段就是一段回文串,使用$Manacher$求解即可。

  1. #include<bits/stdc++.h>
  2. #define ld long double
  3. //This code is written by Itst
  4. using namespace std;
  5.  
  6. inline int read(){
  7. ;
  8. ;
  9. char c = getchar();
  10. while(c != EOF && !isdigit(c)){
  11. if(c == '-')
  12. f = ;
  13. c = getchar();
  14. }
  15. while(c != EOF && isdigit(c)){
  16. a = (a << ) + (a << ) + (c ^ ');
  17. c = getchar();
  18. }
  19. return f ? -a : a;
  20. }
  21.  
  22. , MOD = 1e9 + ;
  23. ] , news[MAXN];
  24. struct comp{
  25. ld x , y;
  26.  
  27. comp(ld _x = , ld _y = ){
  28. x = _x;
  29. y = _y;
  30. }
  31.  
  32. comp operator +(comp a){
  33. return comp(x + a.x , y + a.y);
  34. }
  35.  
  36. comp operator -(comp a){
  37. return comp(x - a.x , y - a.y);
  38. }
  39.  
  40. comp operator *(comp a){
  41. return comp(x * a.x - y * a.y , x * a.y + y * a.x);
  42. }
  43. }A[MAXN];
  44. int need , dir[MAXN] , calc[MAXN] , manacher[MAXN];
  45. );
  46.  
  47. inline int poww(long long a , int b){
  48. ;
  49. while(b){
  50. )
  51. times = times * a % MOD;
  52. a = a * a % MOD;
  53. b >>= ;
  54. }
  55. return times;
  56. }
  57.  
  58. inline void swap(comp& a , comp& b){
  59. comp t = a;
  60. a = b;
  61. b = t;
  62. }
  63.  
  64. inline void FFT(int type){
  65. comp wn , w;
  66. ; i < need ; ++i)
  67. if(i < dir[i])
  68. swap(A[i] , A[dir[i]]);
  69. ; i < need ; i <<= ){
  70. wn = comp(cos(pi / i) , type * sin(pi / i));
  71. ; j < need ; j += i << ){
  72. w = comp( , );
  73. ; k < i ; ++k , w = w * wn){
  74. comp x = A[j + k] , y = A[i + j + k] * w;
  75. A[j + k] = x + y;
  76. A[i + j + k] = x - y;
  77. }
  78. }
  79. }
  80. }
  81. int main(){
  82. #ifndef ONLINE_JUDGE
  83. freopen("4199.in" , "r" , stdin);
  84. //freopen("4199.out" , "w" , stdout);
  85. #endif
  86. scanf("%s" , s);
  87. ;
  88. need = ;
  89. )
  90. need <<= ;
  91. ; i < need ; ++i)
  92. dir[i] = (dir[i >> ] >> ) | (i & ? need >> : );
  93.  
  94. ; i < l ; ++i)
  95. if(s[i] == 'a')
  96. A[i].x = ;
  97. FFT();
  98. ; i < need ; ++i)
  99. A[i] = A[i] * A[i];
  100. FFT(-);
  101. ; i < need ; ++i)
  102. calc[i] = A[i].x / need / + 0.6;
  103.  
  104. memset(&A , , sizeof(A));
  105. ; i < l ; ++i)
  106. if(s[i] == 'b')
  107. A[i].x = ;
  108. FFT();
  109. ; i < need ; ++i)
  110. A[i] = A[i] * A[i];
  111. FFT(-);
  112. ; i < need ; ++i){
  113. calc[i] += A[i].x / need / + 0.6;
  114. sum = (sum + poww( , calc[i]) - ) % MOD;
  115. }
  116.  
  117. ; i < l ; ++i)
  118. news[(i << ) + ] = s[i];
  119. , maxI = ;
  120. ; i < l << ; ++i){
  121. if(maxD > i)
  122. manacher[i] = min(manacher[maxI * - i] , maxD - i - );
  123. && i + manacher[i] <= l << && news[i - manacher[i]] == news[i + manacher[i]])
  124. ++manacher[i];
  125. sum = (sum - (manacher[i] >> ) + MOD) % MOD;
  126. if(i + manacher[i] > maxD){
  127. maxD = i + manacher[i];
  128. maxI = i;
  129. }
  130. }
  131. cout << sum;
  132. ;
  133. }

Luogu4199 万径人踪灭 FFT、Manacher的更多相关文章

  1. BZOJ 3160: 万径人踪灭 [fft manacher]

    3160: 万径人踪灭 题意:求一个序列有多少不连续的回文子序列 一开始zz了直接用\(2^{r_i}-1\) 总-回文子串 后者用manacher处理 前者,考虑回文有两种对称形式(以元素/缝隙作为 ...

  2. BZOJ3160:万径人踪灭(FFT,Manacher)

    Solution $ans=$回文子序列$-$回文子串的数目. 后者可以用$manacher$直接求. 前者设$f[i]$表示以$i$为中心的对称的字母对数. 那么回文子序列的数量也就是$\sum_{ ...

  3. P4199 万径人踪灭 FFT + manacher

    \(\color{#0066ff}{ 题目描述 }\) \(\color{#0066ff}{输入格式}\) 一行,一个只包含a,b两种字符的字符串 \(\color{#0066ff}{输出格式}\) ...

  4. BZOJ 3160: 万径人踪灭 FFT+快速幂+manacher

    BZOJ 3160: 万径人踪灭 题目传送门 [题目大意] 给定一个长度为n的01串,求有多少个回文子序列? 回文子序列是指从原串中找出任意个,使得构成一个回文串,并且位置也是沿某一对称轴对称. 假如 ...

  5. BZOJ3160 万径人踪灭 【fft + manacher】

    题解 此题略神QAQ orz po神牛 由题我们知道我们要求出: 回文子序列数 - 连续回文子串数 我们记为ans1和ans2 ans2可以用马拉车轻松解出,这里就不赘述了 问题是ans1 我们设\( ...

  6. 万径人踪灭(FFT+manacher)

    传送门 这题--我觉得像我这样的菜鸡选手难以想出来-- 题目要求求出一些子序列,使得其关于某个位置是对称的,而且不能是连续一段,求这样的子序列的个数.这个直接求很困难,但是我们可以先求出所有关于某个位 ...

  7. bzoj 3160: 万径人踪灭【FFT+manacher】

    考虑正难则反,我们计算所有对称子序列个数,再减去连续的 这里减去连续的很简单,manacher即可 然后考虑总的,注意到关于一个中心对称的两点下标和相同(这样也能包含以空位为对称中心的方案),所以设f ...

  8. 洛谷P4199 万径人踪灭(manacher+FFT)

    传送门 题目所求为所有的不连续回文子序列个数,可以转化为回文子序列数-回文子串数 回文子串manacher跑一跑就行了,考虑怎么求回文子序列数 我们考虑,如果$S_i$是回文子序列的对称中心,那么只要 ...

  9. BZOJ3160 万径人踪灭(FFT+manacher)

    容易想到先统计回文串数量,这样就去掉了不连续的限制,变为统计回文序列数量. 显然以某个位置为对称轴的回文序列数量就是2其两边(包括自身)对称相等的位置数量-1.对称有啥性质?位置和相等.这不就是卷积嘛 ...

随机推荐

  1. Oracle 11gR2_database在Linux下的安装

    Oracle 11gR2_database在Linux下的安装 by:授客 QQ:1033553122 由于篇幅问题,采用链接分享的形式,烦请复制以下网址,黏贴到浏览器中打开,下载 http://pa ...

  2. Android Studio 通过一个登录功能介绍SQLite数据库的使用

    前言: SQLite简介:是一款轻型的数据库,是遵守ACID的关系型数据库管理系统,它包含在一个相对小的C库中.它是D.RichardHipp建立的公有领域项目.它的设计目标是嵌入式的,而且目前已经在 ...

  3. python变量的命名空间

    首先必须要提一下python程序执行过程中变量的查找规则 较官方的查找机制是: 局部作用域--外部函数作用域--全局作用域--内建函数作用域 其实一般内建函数中的作用域很少会涉及到,因为内建函数其实是 ...

  4. springboot 升级到2.0后 context-path 配置 不起作用,不生效 不管用 皆是因为版本改动导致的在这里记录一下

    不知不觉,新的项目已经将springboot升级为2.0版本了.刚开始没有配置server.contextpath,默认的“/”,然后今天放到自己的服务器上,所以就要规范名称.  结果,失败了,无论我 ...

  5. [cb]ScriptableWizard 创建向导

    需求 方便策划一步一步的创建Actor 思路分析 Unity的Editor中提供创建向导的功能,ScriptableWizard 代码实现 创建一个WizardCreateActor继承自Script ...

  6. Beta冲刺(4/5)(麻瓜制造者)

    今日已完成 邓弘立:完成了商品管理(下架)和搜索功能 符天愉:完成了后台管理员界面的登录和其他视图的载入 江郑:昨天来决定跨域执行请求,后台参考一些意见以后,操作起来没有那么容易实现,和队友交流以后本 ...

  7. 【日常开发】使用多种工具实现 sql查询没有结果的name

    本文地址 分享提纲: 1. 事情的背景 2. 解决办法 3. 总结 1. 事情的背景 现在需要将2000条数据的name,从user表中查询出来结果,sql 这样写 SELECT * FROM use ...

  8. <table>标签总结(colspan跨列 ,rowspan跨行)

    table标签有些内置属性要设置: <table cellpadding="0" cellspacing="0" border="0" ...

  9. Handler实现线程间的通信2

    与Handler实现线程间的通信1反过来MainThread中向WorkerThread中发送消息

  10. P1056 排座椅

    非原创 #include<bits/stdc++.h>using namespace std;int t1[2009];int t2[2009]; int findmax(int *a){ ...