[2017.12.2]FFT學習筆記
阿新 • • 發佈:2017-12-03
修改 img tails closed lex lap efi http main
墻裂推薦兩個博客:
http://blog.csdn.net/iamzky/article/details/22712347 畫了圖,寫的很容易懂,配合《算法導論》服用更佳
http://blog.xlightgod.com/%e3%80%90uoj34%e3%80%91%e5%a4%9a%e9%a1%b9%e5%bc%8f%e4%b9%98%e6%b3%95/ XlightGod大佬的博客,寫的很清楚,模板也非常棒
最後上我自己修改過的XlightGod的模板,符合自己風格
1 #include<bits/stdc++.h> 2 #define N 100010 3 #define RG register 4View Code#define inf 0x3f3f3f3f 5 using namespace std; 6 const double pi=acos(-1); 7 typedef complex<double> C; 8 C a[N],b[N]; 9 int L,m,n,R[N]; 10 inline int gi(){ 11 RG int x=0;RG char y=getchar(); 12 while(y<‘0‘||y>‘9‘) y=getchar(); 13 while(y>=‘0‘&&y<=‘9‘) x=x*10+y-‘0‘,y=getchar(); 14 return x; 15 } 16 inline void fft(C *x,int y){ 17 for (RG int i=0;i<n;++i) 18 if(i<R[i]) 19 swap(x[i],x[R[i]]);//交換位置,數組總要換回來吧 20 for (RG int i=1;i<n;i<<=1){//待合並區間長度 21 C wn(cos(pi/i),sin(y*pi/i)),even,odd; 22 //這裏就不用再*2了,因為合並後的區間長度是i的兩倍(這裏的i可以理解為len/2)23 for (RG int j=0;j<n;j+=i<<1){//起始位置 24 C w(1,0); 25 for (RG int k=0;k<i;++k,w*=wn){//第幾個,類似於遞歸版的for(i~len/2) 26 even=x[j+k]; 27 odd=w*x[j+i+k]; 28 x[j+k]=even+odd; 29 x[j+i+k]=even-odd; 30 } 31 } 32 } 33 } 34 int main(){ 35 freopen("34.in","r",stdin); 36 freopen("34.out","w",stdout); 37 n=gi();m=gi(); 38 for (RG int i=0;i<=n;++i) a[i]=gi(); 39 for (RG int i=0;i<=m;++i) b[i]=gi(); 40 for (m+=n,n=1;n<=m;n<<=1) ++L; 41 for (RG int i=0;i< n;++i) R[i]=(R[i>>1]>>1)|((i&1)<<(L-1));//遞推 42 fft(a,1);fft(b,1); 43 for (RG int i=0;i<=n;++i) a[i]*=b[i]; 44 fft(a,-1); 45 for (RG int i=0;i<=m;++i) printf("%d ",int(a[i].real()/n+0.5)); 46 return 0; 47 }
[2017.12.2]FFT學習筆記