• 1402大数相乘 FFT算法学习!


    网上找的,慢慢研究下

    View Code
      1 #include <cmath>  
    2 #include <complex>
    3 #include <cstring>
    4 using namespace std;
    5
    6 const double PI = acos(-1);
    7 typedef complex<double> cp;
    8 typedef long long int64;
    9
    10 const int N = 1 << 16;
    11 int64 a[N], b[N], c[N << 1];
    12
    13 void bit_reverse_copy(cp a[], int n, cp b[])
    14 {
    15 int i, j, k, u, m;
    16 for (u = 1, m = 0; u < n; u <<= 1, ++m);
    17 for (i = 0; i < n; ++i)
    18 {
    19 j = i; k = 0;
    20 for (u = 0; u < m; ++u, j >>= 1)
    21 k = (k << 1) | (j & 1);
    22 b[k] = a[i];
    23 }
    24 }
    25
    26 void FFT(cp _x[], int n, bool flag)
    27 {
    28 static cp x[N << 1];
    29 bit_reverse_copy(_x, n, x);
    30 int i, j, k, kk, p, m;
    31 for (i = 1, m = 0; i < n; i <<= 1, ++m);
    32 double alpha = 2 * PI;
    33 if (flag) alpha = -alpha;
    34 for (i = 0, k = 2; i < m; ++i, k <<= 1)
    35 {
    36 cp wn = cp(cos(alpha / k), sin(alpha / k));
    37 for (j = 0; j < n; j += k)
    38 {
    39 cp w = 1, u, t;
    40 kk = k >> 1;
    41 for (p = 0; p < kk; ++p)
    42 {
    43 t = w * x[j + p + kk];
    44 u = x[j + p];
    45 x[j + p] = u + t;
    46 x[j + p + kk] = u - t;
    47 w *= wn;
    48 }
    49 }
    50 }
    51 memcpy(_x, x, sizeof(cp) * n);
    52 }
    53
    54 void polynomial_multiply(int64 a[], int na, int64 b[], int nb, int64 c[], int &nc)
    55 {
    56 int i, n;
    57 i = max(na, nb) << 1;
    58 for (n = 1; n < i; n <<= 1);
    59 static cp x[N << 1], y[N << 1];
    60 for (i = 0; i < na; ++i) x[i] = a[i];
    61 for (; i < n; ++i) x[i] = 0;
    62 FFT(x, n, 0);
    63 for (i = 0; i < nb; ++i) y[i] = b[i];
    64 for (; i < n; ++i) y[i] = 0;
    65 FFT(y, n, 0);
    66 for (i = 0; i < n; ++i) x[i] *= y[i];
    67 FFT(x, n, 1);
    68 for (i = 0; i < n; ++i)
    69 {
    70 c[i] =(int64)(x[i].real() / n + 0.5);
    71 }
    72 for (nc = na + nb - 1; nc > 1 && !c[nc - 1]; --nc);
    73 }
    74
    75 const int LEN = 5, MOD = 100000;
    76 void convert(char *s, int64 a[], int &n)
    77 {
    78 int len = strlen(s), i, j, k;
    79 for (n = 0, i = len - LEN; i >= 0; i -= LEN)
    80 {
    81 for (j = k = 0; j < LEN; ++j)
    82 k = k * 10 + (s[i + j] - '0');
    83 a[n++] = k;
    84 }
    85 i += LEN;
    86 if (i)
    87 {
    88 for (j = k = 0; j < i; ++j)
    89 k = k * 10 + (s[j] - '0');
    90 a[n++] = k;
    91 }
    92 }
    93
    94 void print(int64 a[], int n)
    95 {
    96 printf("%I64d", a[--n]);
    97 while (n) printf("%05I64d", a[--n]);
    98 puts("");
    99 }
    100
    101 char buf[N + 10];
    102
    103 int main()
    104 {
    105 int na, nb, nc;
    106
    107 while (scanf("%s", buf) != EOF)
    108 {
    109 bool sign = false;
    110 if (buf[0] == '-')
    111 {
    112 sign = !sign;
    113 convert(buf + 1, a, na);
    114 }
    115 else convert(buf, a, na);
    116 scanf("%s", buf);
    117 if (buf[0] == '-')
    118 {
    119 sign = !sign;
    120 convert(buf + 1, b, nb);
    121 }
    122 else convert(buf, b, nb);
    123 polynomial_multiply(a, na, b, nb, c, nc);
    124 int64 t1, t2;
    125 t1 = 0;
    126 for (int i = 0; i < nc; ++i)
    127 {
    128 t2 = t1 + c[i];
    129 c[i] = t2 % MOD;
    130 t1 = t2 / MOD;
    131 }
    132 for (; t1; t1 /= MOD) c[nc++] = t1 % MOD;
    133 if (sign) putchar('-');
    134 print(c, nc);
    135 }
    136 return 0;
    137 }
  • 相关阅读:
    首篇
    typedef 的几种用法
    ftp 命令
    (zt)STL中的map与hash_map
    (zt)关于UDP网络游戏服务器的一些探讨
    (zt)UDP编程的时候,一次发送多少bytes好?
    (zt)界面技术概述
    (zt)这是对目前大部分平台都适用的内存对齐规则的定义
    (zt)高性能I/O设计模式Reactor和Proactor
    (zt)ACE高效PROACTOR编程框架一ClientHandle
  • 原文地址:https://www.cnblogs.com/bersaty/p/2281186.html
Copyright © 2020-2023  润新知