算法
虽然标题上写着堂堂正正,辉煌的几个字就是本题正解,但是还有比正解更优的做法。
前置知识:二进制 GCD
当你学完二进制 GCD 之后,就可以直接写出代码,但是要记住取模。
代码
#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstring>
#include<algorithm>
#include<vector>
using namespace std;
typedef unsigned long long ull;
const int mod = 998244353;
int a[5003], b[5003], n;
ull gcd(ull a, ull b) { // 二进制 GCD
ull az = __builtin_ctz(a), bz = __builtin_ctz(b);
ull z = min(az, bz);
b >>= bz;
while (a) {
a >>= az;
int tmp = a - b;
az = __builtin_ctz(tmp);
b = min(a, b), a = abs(tmp);
}
return b << z;
}
signed main() {
scanf("%d", &n);
for (int i = 1; i <= n; i++) scanf("%d", &a[i]);
for (int i = 1; i <= n; i++) scanf("%d", &b[i]);
for (int i = 1; i <= n; i++) {
ull ans = 0, k = i;
for (int j = 1; j <= n; j++) {
// 注意取模
ans = (ans + (k * gcd(a[i], b[j]) % mod)) % mod;
k = k * i % mod;
}
printf("%llu\n", ans);
}
return 0;
}

852

被折叠的 条评论
为什么被折叠?



