# bzoj 4259 残缺的字符串 FFT

## 残缺的字符串

Time Limit: 10 Sec  Memory Limit: 128 MB
Submit: 1327  Solved: 300
[Submit][Status][Discuss]

3 7
a*b
aebr*ob

2
1 5

## Source

[Submit][Status][Discuss]

然后第二个翻转卷积就ok了。

 1 #include<cstring>
2 #include<iostream>
3 #include<cstdio>
4 #include<algorithm>
5 #include<cmath>
6
7 #define ll long long
8 #define N 1<<20
9 #define pi acos(-1)
10 using namespace std;
12 {
13     int x=0,f=1;char ch=getchar();
14     while(!isdigit(ch)){if(ch=='-')f=-1;ch=getchar();}
15     while(isdigit(ch)){x=(x<<1)+(x<<3)+ch-'0';ch=getchar();}
16     return x*f;
17 }
18
19 int n,m,hjq,res,num,L;
20 int c[N],d[N],rev[N];
21 char ch[N];
22
23 struct comp
24 {
25     double r,v;
26     comp(){r=v=0.0;}
27     comp(double a,double b){r=a,v=b;}
28     friend inline comp operator+(comp x,comp y){return comp(x.r+y.r,x.v+y.v);}
29     friend inline comp operator-(comp x,comp y){return comp(x.r-y.r,x.v-y.v);}
30     friend inline comp operator*(comp x,comp y){return comp(x.r*y.r-x.v*y.v,x.r*y.v+x.v*y.r);}
31 }a1[N],b1[N],a2[N],b2[N],a3[N],b3[N],fzy[N];
32
33 void FFT(comp *a,int flag)
34 {
35     for (int i=0;i<num;i++)
36         if (i<rev[i]) swap(a[i],a[rev[i]]);
37     for (int i=1;i<num;i<<=1)
38     {
39         comp wn=comp(cos(pi/i),flag*sin(pi/i));
40         for (int j=0;j<num;j+=(i<<1))
41         {
42             comp w=comp(1,0);
43             for (int k=0;k<i;k++,w=w*wn)
44             {
45                 comp x=a[j+k],y=w*a[j+k+i];
46                 a[j+k]=x+y,a[j+k+i]=x-y;
47             }
48         }
49     }
50     if (flag==-1) for (int i=0;i<num;i++) a[i].r/=num;
51 }
52 int main()
53 {
55     scanf("%s",ch);for (int i=0;i<m;i++) d[i]=(ch[m-i-1]=='*')?0:ch[m-i-1]-'a'+1;
56     scanf("%s",ch);for (int i=0;i<n;i++) c[i]=(ch[i]=='*')?0:ch[i]-'a'+1;
57
58     for (num=1;num<=n+m-1;num<<=1,L++);if (L) L--;
59     for (int i=0;i<num;i++) rev[i]=(rev[i>>1]>>1)|((i&1)<<L);
60
61     for (int i=0;i<n;i++) a1[i].r=c[i]*c[i]*c[i];
62     for (int i=0;i<m;i++) b1[i].r=d[i];
63     for (int i=0;i<n;i++) a2[i].r=-2*c[i]*c[i];
64     for (int i=0;i<m;i++) b2[i].r=d[i]*d[i];
65     for (int i=0;i<n;i++) a3[i].r=c[i];
66     for (int i=0;i<m;i++) b3[i].r=d[i]*d[i]*d[i];
67
68     FFT(a1,1),FFT(b1,1),FFT(a2,1),FFT(b2,1),FFT(a3,1),FFT(b3,1);
69     for (int i=0;i<num;i++) fzy[i]=a1[i]*b1[i]+a2[i]*b2[i]+a3[i]*b3[i];
70     FFT(fzy,-1);
71
72     for (int i=m-1;i<n;i++) if (!(ll)(fzy[i].r+0.5)) res++;
73     printf("%d\n",res);
74     for (int i=m-1;i<n;i++)
75         if (!(ll)(fzy[i].r+0.5)) printf("%d ",i-m+2);
76 }

posted @ 2018-03-31 14:16  Kaiser-  阅读(92)  评论(0编辑  收藏  举报