请问为什么这么写线性筛是错误的
查看原帖
请问为什么这么写线性筛是错误的
235679
Happig楼主2020/9/29 21:33

对于dnμ(d)d\sum_{d|n}\mu(d)d,根据狄利克雷卷积这是一个积性函数,明显可以线性筛的吧,但是不知道代码为什么错误,感觉没啥问题

//
// Created by Happig on 2020/9/29
//
#include <bits/stdc++.h>
#include <unordered_map>
#include <unordered_set>

using namespace std;
#define fi first
#define se second
#define pb push_back
#define ins insert
#define Vector Point
#define ENDL "\n"
#define lowbit(x) (x&(-x))
#define mkp(x, y) make_pair(x,y)
#define mem(a, x) memset(a,x,sizeof a);
typedef long long ll;
typedef long double ld;
typedef unsigned long long ull;
typedef pair<int, int> pii;
typedef pair<ll, ll> pll;
typedef pair<double, double> pdd;
const double eps = 1e-8;
const double pi = acos(-1.0);
const int inf = 0x3f3f3f3f;
const double dinf = 1e300;
const ll INF = 1e18;
const int Mod = 1e9 + 7;
const int maxn = 5e4 + 10;

int cnt[maxn], mu[maxn];
ll f[maxn];
vector<int> prime;
bitset<maxn> vis;

void init() {
    vis.reset(), prime.clear();
    f[1] = 1;
    for (int i = 2; i < maxn; i++) {
        if (!vis[i]) {
            prime.push_back(i);
            f[i] = 1 - i;
            mu[i] = -1;
        }
        for (int j = 0; j < prime.size() && i * prime[j] < maxn; j++) {
            vis[i * prime[j]] = 1;
            if (i % prime[j]) {
                f[i * prime[j]] = f[i] * f[prime[j]];
                mu[i * prime[j]] = -mu[i];
            } else {
                f[i * prime[j]] = f[i];
                mu[i * prime[j]] = 0;
                break;
            }
        }
    }
    for (int i = 1; i < maxn; i++) f[i] += f[i - 1];
//    for (int i = 1; i < maxn; i++) {
//        for (int j = i; j < maxn; j += i) {
//            f[j] += 1LL * mu[i] * i;
//        }
//    }
}


int main() {
    //freopen("in.txt","r",stdin);
    //freopen("out.txt","w",stdout);
    ios_base::sync_with_stdio(0), cin.tie(0), cout.tie(0);
    int n, m = 0;
    init();
    cin >> n;
    for (int i = 1, x; i <= n; i++) {
        cin >> x;
        cnt[x]++;
        m = max(m, x);
    }
    n = m;
    ll ans = 0;
    for (int i = 1; i <= n; i++) {
        ll res = 0;
        for (int j = 1; j <= n / i; j++) {
            res += 1LL * j * cnt[j * i];
        }
        ans += res * res * i * f[i];
    }
    cout << ans << ENDL;
    return 0;
}

2020/9/29 21:33
加载中...