wtyqwq @ 2020-03-23 19:55:43
把
#pragma GCC optimize(3)
#pragma GCC optimize("Ofast")
#include <cstdio>
#include <cmath>
#include <cctype>
#include <iomanip>
#define R register
#define N (1 << 17)
#define int long long
#define ll int
#define double long double
#define PI 3.141592653589793238462643383279502884
using namespace std;
char Buf[1 << 24], *S = Buf, *T = Buf;
//#define getchar() (S == T && (T = (S = Buf) + fread(Buf, 1, 1 << 24, stdin), S == T) ? EOF : *S++)
inline int input() {
R int x(0), f(0);
R char c(getchar());
while (!isdigit(c)) f |= (c == '-'), c = getchar();
while (isdigit(c)) x = (x << 1) + (x << 3) + (c ^ 48), c = getchar();
return f ? -x : x;
}
struct complex {
double x, y;
inline complex(double x = 0, double y = 0) : x(x), y(y) {}
inline complex operator+(const complex b) const { return complex(x + b.x, y + b.y); }
inline complex operator-(const complex b) const { return complex(x - b.x, y - b.y); }
inline complex operator*(const complex b) const { return complex(x * b.x - y * b.y, x * b.y + y * b.x); }
};
int n, m, t, lim, k, mod;
int rev[N << 2], ans[N << 1];
complex a[N << 2], b[N << 2], c[N << 2], d[N << 2], X[N << 2];
inline void FFT(complex *f, int flag) {
for (int i = 0; i < lim; ++i)
if (i < rev[i])
swap(f[i], f[rev[i]]);
for (R int l = 2; l <= lim; l <<= 1) {
int len = l >> 1;
R complex OMG(cos(PI / len), sin(PI / len));
OMG.y *= flag;
for (R int k = 0; k < lim; k += l) {
R complex buf(1, 0);
for (R int i = k; i < k + len; ++i) {
complex tmp = buf * f[len + i];
f[len + i] = f[i] - tmp, f[i] = f[i] + tmp, buf = buf * OMG;
}
}
}
}
inline double Round(double x) {
if (x == 0)
return x;
x > 0 ? x += 0.5 : x -= 0.5;
return x;
}
inline void solve(complex *a, complex *b, int res) {
for (R int i = 0; i < lim; ++i) X[i] = a[i] * b[i];
FFT(X, -1);
//for (R int i = 0; i < lim; ++i) printf("%.5lf\n", X[i]);
for (R int i = 0; i <= t; ++i) ans[i] = (ll)((ll)ans[i] + (ll)Round(X[i].x / lim) % (ll)mod * (ll)res % mod) % mod;
}
inline void MTT(complex *a, complex *b, complex *c, complex *d) {
FFT(a, 1), FFT(b, 1), FFT(c, 1), FFT(d, 1);
//for (int i = 0; i < lim; ++i) printf("%.4lf\n", a[i]);
//for (int i = 0; i < lim; ++i) printf("%.4lf\n", b[i]);
//for (int i = 0; i < lim; ++i) printf("%.4lf\n", c[i]);
//for (int i = 0; i < lim; ++i) printf("%.4lf\n", d[i]);
solve(a, c, (1ll << 30) % mod), solve(a, d, (1 << 15) % mod);
solve(c, b, (1ll << 15) % mod), solve(b, d, 1);
}
signed main() {
n = input(), m = input(), mod = input();
for (int i = 0; i <= n; ++i) {
int x = input();
a[i].x = (double)(x >> 15ll);
c[i].x = (double)(x & ((1ll << 15ll) - 1ll));
//printf("%.4lf %.4lf\n", a[i].x, c[i].x);
}
for (int i = 0; i <= m; ++i) {
int x = input();
b[i].x = (double)(x >> 15ll);
d[i].x = (double)(x & ((1ll << 15) - 1ll));
}
for (t = n + m, lim = 1ll; lim <= t;) lim <<= 1, ++k;
for (int i = 0ll; i < lim; ++i) rev[i] = (rev[i >> 1] >> 1) | ((i & 1) << (k - 1));
MTT(a, c, b, d);
for (int i = 0ll; i <= t; ++i) printf("%lld ", ans[i]);
return 0;
}
by EternalEpic @ 2020-03-23 19:59:34
这年头8次FFT。。。
去看MYY的论文吧,4次FFT的。
或者这个5次FFT的伪MTT
by EternalEpic @ 2020-03-23 19:59:43
@Oler_Accepted
by EternalEpic @ 2020-03-23 20:00:29
@Oler_Accepted 看样子你精度掉的厉害啊。
by iostream @ 2020-03-23 20:00:54
单位根不要现算
by wtyqwq @ 2020-03-23 20:06:29
@LJB00131 有啊 Round函数
by LJB00131 @ 2020-03-23 20:07:54
@Oler_Accepted 是我菜了qwq
by LJB00131 @ 2020-03-23 20:10:52
@Oler_Accepted 你掉精度了吧(
你看看参照那篇7次fft的题解能不能过
by wtyqwq @ 2020-03-23 20:12:49
找到一篇题解,和我的差不多
8次FFT
by wtyqwq @ 2020-03-23 20:14:22
@刘兆洲 @iostream 求教(黄√大佬),他为什么可以过。。。
by Smile_Cindy @ 2020-03-23 20:14:56
@Oler_Accepted 那不叫黄勾那叫金勾