2216. 你猜是不是KMP

★★★☆   输入文件:guess.in   输出文件:guess.out   简单对比
时间限制:1 s   内存限制:256 MB

【题目描述】

  XX在玩两个串的游戏。首先,他拿出了两个字符串 S 和 T,XX想知道 T在 S 中出现了几次,分别在哪些位置出现。注意 T 中可能有“?”字符,这个字符可以匹配任何字符。

【输入格式】

  两行两个字符串,分别代表 S 和 T

【输出格式】

  第一行一个正整数 k,表示 T 在 S 中出现了几次。

  接下来 k 行正整数,

  分别代表 T 每次在 S 中出现的开始位置。按照从小到大

  的顺序输出,S 下标从 0 开始。

【样例输入】

  ababcadaca

  a?a

【样例输出】

  3

  0

  5

  7

【提示】

  对于 10%的数据, S 和 T 的长度不超过 100

  对于另外 20%的数据,T 中无“?”

  对于 100%的数据,S 长度不超过 10^5,T 长度不会超过 S。S 中只包含小写

  字母,T 中只包含小写字母和“?”

【来源】

  经典题目

  

  这道题咩,是FFT哦,咳咳……

 #include <iostream>
#include <cstring>
#include <cstdio>
#include <cmath>
using namespace std;
const int maxn=;
const double PI=acos(-1.0);
char s[maxn],t[maxn];
int a[maxn],b[maxn];
struct complex{
double r,i;
complex(double r_=0.0,double i_=0.0){
r=r_;i=i_;
}
complex operator +(complex a){
return complex(r+a.r,i+a.i);
}
complex operator -(complex a){
return complex(r-a.r,i-a.i);
}
complex operator *(complex a){
return complex(r*a.r-i*a.i,r*a.i+i*a.r);
}
};
complex A[maxn],B[maxn],C[maxn],D[maxn],E[maxn]; void Rader(complex *a,int len){
int k;
for(int i=,j=len>>;i<len-;i++){
if(i<j)swap(a[i],a[j]);
k=len>>;
while(j>=k){
j-=k;
k>>=;
}
j+=k;
}
} void FFT(complex *a,int len,int on){
Rader(a,len);
for(int h=;h<=len;h<<=){
complex wn(cos(-on*PI*2.0/h),sin(-on*PI*2.0/h));
for(int j=;j<len;j+=h){
complex w(,);
for(int k=j;k<j+(h>>);k++){
complex u=a[k];
complex v=a[k+(h>>)]*w;
a[k]=u+v;
a[k+(h>>)]=u-v;
w=w*wn;
}
}
}
if(on==-)
for(int i=;i<len;i++)
a[i].r/=len;
}
int ans[maxn],tot;
int main(){
freopen("guess.in","r",stdin);
freopen("guess.out","w",stdout);
scanf("%s%s",s,t);
int lens=strlen(s);
int lent=strlen(t);
for(int i=;i<lens;i++)
a[i]=s[i]-'a'+;
for(int i=;i<lent;i++){
if(t[i]=='?')
b[lent-i-]=;
else
b[lent-i-]=t[i]-'a'+;
} int len=;
while(len<=lens+lent)len<<=; for(int i=;i<lens;i++)A[i]=complex(1.0,);
for(int i=;i<lent;i++)B[i]=complex(1.0*b[i]*b[i]*b[i],);
FFT(A,len,);FFT(B,len,);
for(int i=;i<len;i++)C[i]=A[i]*B[i];
FFT(C,len,-); memset(A,,sizeof(A));
memset(B,,sizeof(B));
for(int i=;i<lens;i++)A[i]=complex(2.0*a[i],);
for(int i=;i<lent;i++)B[i]=complex(1.0*b[i]*b[i],);
FFT(A,len,);FFT(B,len,);
for(int i=;i<len;i++)D[i]=A[i]*B[i];
FFT(D,len,-); memset(A,,sizeof(A));
memset(B,,sizeof(B));
for(int i=;i<lens;i++)A[i]=complex(1.0*a[i]*a[i],);
for(int i=;i<lent;i++)B[i]=complex(1.0*b[i],);
FFT(A,len,);FFT(B,len,);
for(int i=;i<len;i++)E[i]=A[i]*B[i];
FFT(E,len,-); for(int i=lent-;i<lens;i++)
if(fabs(C[i].r-D[i].r+E[i].r)<1e-)
ans[++tot]=i-lent+; printf("%d\n",tot);
for(int i=;i<=tot;i++)
printf("%d\n",ans[i]);
return ;
}

快速傅里叶变换(FFT):COGS 2216. 你猜是不是KMP的更多相关文章

  1. [学习笔记] 多项式与快速傅里叶变换(FFT)基础

    引入 可能有不少OIer都知道FFT这个神奇的算法, 通过一系列玄学的变化就可以在 $O(nlog(n))$ 的总时间复杂度内计算出两个向量的卷积, 而代码量却非常小. 博主一年半前曾经因COGS的一 ...

  2. 多项式 之 快速傅里叶变换(FFT)/数论变换(NTT)/常用套路【入门】

    原文链接https://www.cnblogs.com/zhouzhendong/p/Fast-Fourier-Transform.html 多项式 之 快速傅里叶变换(FFT)/数论变换(NTT)/ ...

  3. 快速傅里叶变换FFT

    多项式乘法 #include <cstdio> #include <cmath> #include <algorithm> #include <cstdlib ...

  4. 快速傅里叶变换FFT& 数论变换NTT

    相关知识 时间域上的函数f(t)经过傅里叶变换(Fourier Transform)变成频率域上的F(w),也就是用一些不同频率正弦曲线的加 权叠加得到时间域上的信号. \[ F(\omega)=\m ...

  5. 快速傅里叶变换(FFT)

    扯 去北京学习的时候才系统的学习了一下卷积,当时整理了这个笔记的大部分.后来就一直放着忘了写完.直到今天都腊月二十八了,才想起来还有个FFT的笔记没整完呢.整理完这个我就假装今年的任务全都over了吧 ...

  6. 快速傅里叶变换(FFT)_转载

    FFTFFT·Fast  Fourier  TransformationFast  Fourier  Transformation快速傅立叶变换 P3803 [模板]多项式乘法(FFT) 参考上文 首 ...

  7. 基于python的快速傅里叶变换FFT(二)

    基于python的快速傅里叶变换FFT(二)本文在上一篇博客的基础上进一步探究正弦函数及其FFT变换. 知识点  FFT变换,其实就是快速离散傅里叶变换,傅立叶变换是数字信号处理领域一种很重要的算法. ...

  8. 浅谈范德蒙德(Vandermonde)方阵的逆矩阵的求法以及快速傅里叶变换(FFT)中IDFT的原理

    浅谈范德蒙德(Vandermonde)方阵的逆矩阵与拉格朗日(Lagrange)插值的关系以及快速傅里叶变换(FFT)中IDFT的原理 标签: 行列式 矩阵 线性代数 FFT 拉格朗日插值 只要稍微看 ...

  9. 快速傅里叶变换FFT / NTT

    目录 FFT 系数表示法 点值表示法 复数 DFT(离散傅里叶变换) 单位根的性质 FFT(快速傅里叶变换) IFFT(快速傅里叶逆变换) NTT 阶 原根 扩展知识 FFT 参考blog: 十分简明 ...

随机推荐

  1. 21、javascript 基础

    Javascript Javascript 是一种嵌入到HTML文档的脚本语言,由浏览器解释和执行,无需编译. Javascript 是大小写敏感的,大写字母与小写字母不同. 使用“:”分号来分割每一 ...

  2. Css3渐变实例Demo(一)

    1.指定渐变背景的大小 .div { background: url(../img/1.jpg); /*background-size:contain;*/ width: 500px; height: ...

  3. WPF FindName()没找到指定名称的元素

    1.FindName()说明,可以用来获取已经注册名称的元素或标签 // // 摘要: // 查找具有提供的标识符名的元素. // // 参数: // name: // 所请求元素的名称. // // ...

  4. move file create directory.

    If we want to move file to the directory that does not exist,and if we perform a File.Move,it will r ...

  5. Windows的计划任务

    阅读目录 一:什么是Windows的计划任务? 二:如何设置计划任务 三:高级设置计划任务 一:什么是Windows的计划任务? 在日常的工作中,我们都有一些固定的或临时性的工作,而每次在爱机前一坐, ...

  6. oracle 中查看一张表是否有主键,主键在哪个字段上的语句怎么查如要查aa表,

    select a.constraint_name, a.column_name from user_cons_columns a, user_constraints b where a.constra ...

  7. 在window系统下配置login.sql

    在window系统下配置login.sql 他的位置是登录用户的文件夹,我的win7系统位置是: C:\Users\Administrator 我的login.sql下载地址: http://file ...

  8. style currentStyle getComputedStyle的区别和用法

    先介绍下层叠样式表的三种形式: 1.内联样式,在html标签中style属性设置. <p style="color:#f90">内联样式</p> 2.嵌入样 ...

  9. javascript基础学习(四)

    javascript之流程控制语句 学习要点: 表达式语句含义 选择语句:if.if...else.switch 循环语句:while.do...while.for.for...in 跳转语句:bre ...

  10. 非注解SpringMVC

    <!-- SpringMVC前端控制器 --> <servlet> <servlet-name>springmvc</servlet-name> < ...