Luogu4199 万径人踪灭 FFT、Manacher
先不考虑”不是连续的一段“这一个约束条件。可以知道:第$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$求解即可。
#include<bits/stdc++.h>
#define ld long double
//This code is written by Itst
using namespace std;
inline int read(){
;
;
char c = getchar();
while(c != EOF && !isdigit(c)){
if(c == '-')
f = ;
c = getchar();
}
while(c != EOF && isdigit(c)){
a = (a << ) + (a << ) + (c ^ ');
c = getchar();
}
return f ? -a : a;
}
, MOD = 1e9 + ;
] , news[MAXN];
struct comp{
ld x , y;
comp(ld _x = , ld _y = ){
x = _x;
y = _y;
}
comp operator +(comp a){
return comp(x + a.x , y + a.y);
}
comp operator -(comp a){
return comp(x - a.x , y - a.y);
}
comp operator *(comp a){
return comp(x * a.x - y * a.y , x * a.y + y * a.x);
}
}A[MAXN];
int need , dir[MAXN] , calc[MAXN] , manacher[MAXN];
);
inline int poww(long long a , int b){
;
while(b){
)
times = times * a % MOD;
a = a * a % MOD;
b >>= ;
}
return times;
}
inline void swap(comp& a , comp& b){
comp t = a;
a = b;
b = t;
}
inline void FFT(int type){
comp wn , w;
; i < need ; ++i)
if(i < dir[i])
swap(A[i] , A[dir[i]]);
; i < need ; i <<= ){
wn = comp(cos(pi / i) , type * sin(pi / i));
; j < need ; j += i << ){
w = comp( , );
; k < i ; ++k , w = w * wn){
comp x = A[j + k] , y = A[i + j + k] * w;
A[j + k] = x + y;
A[i + j + k] = x - y;
}
}
}
}
int main(){
#ifndef ONLINE_JUDGE
freopen("4199.in" , "r" , stdin);
//freopen("4199.out" , "w" , stdout);
#endif
scanf("%s" , s);
;
need = ;
)
need <<= ;
; i < need ; ++i)
dir[i] = (dir[i >> ] >> ) | (i & ? need >> : );
; i < l ; ++i)
if(s[i] == 'a')
A[i].x = ;
FFT();
; i < need ; ++i)
A[i] = A[i] * A[i];
FFT(-);
; i < need ; ++i)
calc[i] = A[i].x / need / + 0.6;
memset(&A , , sizeof(A));
; i < l ; ++i)
if(s[i] == 'b')
A[i].x = ;
FFT();
; i < need ; ++i)
A[i] = A[i] * A[i];
FFT(-);
; i < need ; ++i){
calc[i] += A[i].x / need / + 0.6;
sum = (sum + poww( , calc[i]) - ) % MOD;
}
; i < l ; ++i)
news[(i << ) + ] = s[i];
, maxI = ;
; i < l << ; ++i){
if(maxD > i)
manacher[i] = min(manacher[maxI * - i] , maxD - i - );
&& i + manacher[i] <= l << && news[i - manacher[i]] == news[i + manacher[i]])
++manacher[i];
sum = (sum - (manacher[i] >> ) + MOD) % MOD;
if(i + manacher[i] > maxD){
maxD = i + manacher[i];
maxI = i;
}
}
cout << sum;
;
}
Luogu4199 万径人踪灭 FFT、Manacher的更多相关文章
- BZOJ 3160: 万径人踪灭 [fft manacher]
3160: 万径人踪灭 题意:求一个序列有多少不连续的回文子序列 一开始zz了直接用\(2^{r_i}-1\) 总-回文子串 后者用manacher处理 前者,考虑回文有两种对称形式(以元素/缝隙作为 ...
- BZOJ3160:万径人踪灭(FFT,Manacher)
Solution $ans=$回文子序列$-$回文子串的数目. 后者可以用$manacher$直接求. 前者设$f[i]$表示以$i$为中心的对称的字母对数. 那么回文子序列的数量也就是$\sum_{ ...
- P4199 万径人踪灭 FFT + manacher
\(\color{#0066ff}{ 题目描述 }\) \(\color{#0066ff}{输入格式}\) 一行,一个只包含a,b两种字符的字符串 \(\color{#0066ff}{输出格式}\) ...
- BZOJ 3160: 万径人踪灭 FFT+快速幂+manacher
BZOJ 3160: 万径人踪灭 题目传送门 [题目大意] 给定一个长度为n的01串,求有多少个回文子序列? 回文子序列是指从原串中找出任意个,使得构成一个回文串,并且位置也是沿某一对称轴对称. 假如 ...
- BZOJ3160 万径人踪灭 【fft + manacher】
题解 此题略神QAQ orz po神牛 由题我们知道我们要求出: 回文子序列数 - 连续回文子串数 我们记为ans1和ans2 ans2可以用马拉车轻松解出,这里就不赘述了 问题是ans1 我们设\( ...
- 万径人踪灭(FFT+manacher)
传送门 这题--我觉得像我这样的菜鸡选手难以想出来-- 题目要求求出一些子序列,使得其关于某个位置是对称的,而且不能是连续一段,求这样的子序列的个数.这个直接求很困难,但是我们可以先求出所有关于某个位 ...
- bzoj 3160: 万径人踪灭【FFT+manacher】
考虑正难则反,我们计算所有对称子序列个数,再减去连续的 这里减去连续的很简单,manacher即可 然后考虑总的,注意到关于一个中心对称的两点下标和相同(这样也能包含以空位为对称中心的方案),所以设f ...
- 洛谷P4199 万径人踪灭(manacher+FFT)
传送门 题目所求为所有的不连续回文子序列个数,可以转化为回文子序列数-回文子串数 回文子串manacher跑一跑就行了,考虑怎么求回文子序列数 我们考虑,如果$S_i$是回文子序列的对称中心,那么只要 ...
- BZOJ3160 万径人踪灭(FFT+manacher)
容易想到先统计回文串数量,这样就去掉了不连续的限制,变为统计回文序列数量. 显然以某个位置为对称轴的回文序列数量就是2其两边(包括自身)对称相等的位置数量-1.对称有啥性质?位置和相等.这不就是卷积嘛 ...
随机推荐
- 【读书笔记】iOS-Interface Builder
IBOutlet或IBAction符号对编译不产生任何影响,它们只是标记,用于告诉Xcode这些对象可以和UI控件进行关联,以便于在编辑Interface Builder上的UI控件的时候Xcode可 ...
- MySQL高可用方案--MHA原理
简介 MHA(Master High Availability)目前在MySQL高可用方面是一个相对成熟的解决方案,它由日本DeNA公司youshimaton(现就职于Facebook公司)开发,是日 ...
- RxJava2.0的使用详解
RxJava2.0的使用详解 1,初识RxJava RxJava就是一种用Java语言实现的响应式编程,来创建基于事件的异步程序 RxJava是一个基于事件订阅的异步执行的一个类库,目前比较火的一些技 ...
- recovery 升级过程执行自定义shell命令
有时候我们需要,在升级的过程中,执行一些shell命令,来完成我们的一些需求,利用升级过程,进行一些特殊化的操作,思路如下: 第一: 把我们需要执行的命令,写成一个test.sh脚本,然后在recov ...
- java中传值方式的个人理解
前言 这几天在整理java基础知识方面的内容,对于值传递还不是特别理解,于是查阅了一些资料和网上相关博客,自己进行了归纳总结,最后将其整理成了一篇博客. 值传递 值传递是指在调用函数时将实际参数复制一 ...
- html 知识整理
一. 前言 本文全面介绍了html的定义.使用和具体常用标签. 参考资料:菜鸟教程 二.定义 html是HyperText Markup Language的简称,也就是超文本标记语言的缩写.通过htm ...
- tkinter中frame布局控件
frame控件 frame控件是将窗口分成好几个小模块,然后每个小模块中添加控件. 也就是将窗口合理的布局 由于和其他控件的操作基本一致,就不做注释了 import tkinter wuya = tk ...
- 常用css字体英文写法
font-family: 'Microsoft Yahei',sans-serif; 宋体:SimSun 黑体:SimHei
- Intel P4 CPU
1. P4 CPU 结构 奔4处理器是Intel的经典之作,它是采用乱序执行内核的超标量处理器.P4采用的微架构称为 Net Burst,基本结构如下: 奔4处理器微架构被分成了4大部分: (1)存储 ...
- 解析oracle的rownum(转)
解析oracle的rownum 本人最近在使用oracle的rownum实现分页显示的时候,对rownum做了进一步的分析和研究.现归纳如下,希望能给大家带来收获. 对于rownum来说它是 ...