FFT学习

来源:互联网 发布:入于找不到网络路径 编辑:程序博客网 时间:2024/05/02 00:53

首先推荐一个学习链接:点击打开链接


HDU1402 FFT入门

/*    题意: 给你两个数A和B, 让你求出C, C = A*B    tag: FFT    分析:我们可以将A和B分解成多项式,比如123可以分解为1*x^2 + 2*x + 3 (x = 10),然后A*B就是将两个多项式相乘得到结果后将10带入    即可。*/#include <cstdio>#include <algorithm>#include <cstring>#include <cmath>using namespace std;const double PI = acos(-1.0);struct Complex {    double r, i;    Complex(double _r=0.0, double _i=0.0) {        r = _r; i = _i;    }    Complex operator +(const Complex &b) {        return Complex(r + b.r, i+b.i);    }    Complex operator -(const Complex &b) {        return Complex(r-b.r, i-b.i);    }    Complex operator *(const Complex &b) {        return Complex(r*b.r-i*b.i, r*b.i+i*b.r);    }};void change(Complex y[], int len) {    int i, j, k;    for(i=1, j=len/2; i<len-1; i++) {        if(i < j) swap(y[i], y[j]);        k = len/2;        while(j >= k){            j -= k;            k /= 2;        }        if(j < k) j += k;    }}void fft(Complex y[], int len, int on) {    change(y, len);    for(int h=2; h<=len; h<<=1) {        Complex wn(cos(-on*2*PI/h), sin(-on*2*PI/h));        for(int j=0; j<len; j+=h) {            Complex w(1, 0);            for(int k=j; k<j+h/2; k++) {                Complex u = y[k];                Complex t = w*y[k+h/2];                y[k] = u + t;                y[k+h/2] = u - t;                w = w*wn;            }        }    }    if(on == -1) {        for(int i=0; i<len; i++)            y[i].r /= len;    }}const int maxn = 600000 + 100;char num1[maxn], num2[maxn];Complex A[maxn], B[maxn];Complex C[maxn];int xi[maxn];int main() {    while(scanf("%s%s", num1, num2) == 2) {        int len1 = strlen(num1), len2 = strlen(num2);        int len = 1;        while(len<len1*2 || len < len2*2) len *= 2;        for(int i=0; i<len1; i++) A[i] = Complex(num1[len1-1-i]-'0', 0);        for(int i=len1; i<len; i++) A[i] = Complex(0, 0);        for(int i=0; i<len2; i++) B[i] = Complex(num2[len2-1-i]-'0', 0);        for(int i=len2; i<len; i++) B[i] = Complex(0, 0);        fft(A, len, 1);     fft(B, len, 1);        for(int i=0; i<len; i++)            C[i] = A[i] * B[i];        fft(C, len, -1);        xi[len] = 0;        for(int i=0; i<len; i++)            xi[i] = (int)(C[i].r + 0.5);        for(int i=0; i<len; i++) {            xi[i+1] += xi[i]/10;            xi[i] %= 10;        }        while(xi[len]==0&&len>=0)            len--;        if(len == -1) printf("0");        else            for(int i=len; i>=0; i--) printf("%d", xi[i]);        printf("\n");    }    return 0;}



0 0