【BZOJ2154】Crash的数字表格(莫比乌斯反演)(数学)

题目大意:

i=1nj=1mlcm(i,j) ∑ i = 1 n ∑ j = 1 m l c m ( i , j )

题解:

ans=i=1nj=1mlcm(i,j)=i=1nj=1mijgcd(i,j) a n s = ∑ i = 1 n ∑ j = 1 m l c m ( i , j ) = ∑ i = 1 n ∑ j = 1 m i j g c d ( i , j )

f(x,y,d)=1in1jmgcd(i,j)=dij f ( x , y , d ) = ∑ 1 ≤ i ≤ n 1 ≤ j ≤ m g c d ( i , j ) = d i j

F(x,y,d)=d|kf(x,y,k)=1in1jmd|gcd(i,j)ij=d21ind1jmdij=d2nd(nd+1)2md(md+1)2 F ( x , y , d ) = ∑ d | k f ( x , y , k ) = ∑ 1 ≤ i ≤ n 1 ≤ j ≤ m d | g c d ( i , j ) i j = d 2 ∑ 1 ≤ i ≤ ⌊ n d ⌋ 1 ≤ j ≤ ⌊ m d ⌋ i j = d 2 ⌊ n d ⌋ ( ⌊ n d ⌋ + 1 ) 2 ⌊ m d ⌋ ( ⌊ m d ⌋ + 1 ) 2


ans=d=1min(n,m)d2×f(nd,md,1)d=d=1min(n,m)d×f(nd,md,1) a n s = ∑ d = 1 m i n ( n , m ) d 2 × f ( ⌊ n d ⌋ , ⌊ m d ⌋ , 1 ) d = ∑ d = 1 m i n ( n , m ) d × f ( ⌊ n d ⌋ , ⌊ m d ⌋ , 1 )

f(x,y,1)=d=1min(x,y)μ(k)F(x,y,k)=k=1min(x,y)μ(k)k2xk(xk+1)2yk(yk+1)2 f ( x , y , 1 ) = ∑ d = 1 m i n ( x , y ) μ ( k ) F ( x , y , k ) = ∑ k = 1 m i n ( x , y ) μ ( k ) k 2 ⌊ x k ⌋ ( ⌊ x k ⌋ + 1 ) 2 ⌊ y k ⌋ ( ⌊ y k ⌋ + 1 ) 2

可以做了

代码:

#include<cstdio>
#include<algorithm>
using namespace std;
const long long MOD=20101009LL,MAXN=10000005LL;
long long sum_mu[MAXN],prime[MAXN/3LL],pcnt;
bool noprime[MAXN];

void init_mu(int);
long long solve(long long,long long);
long long f(long long,long long);
long long sum(long long,long long);

int main()
{
    long long n,m;
    scanf("%lld%lld",&n,&m);
    init_mu(min(n,m));
    printf("%lld\n",solve(n,m));
    return 0;
}

void init_mu(int N)
{
    noprime[1]=1;
    sum_mu[1]=1LL;
    for(long long i=2LL;i<=N;i++)
    {
        if(!noprime[i])
        {
            prime[++pcnt]=i;
            sum_mu[i]=-1LL;
        }
        for(long long j=1;j<=pcnt&&i*prime[j]<=N;j++)
        {
            noprime[i*prime[j]]=1;
            if(i%prime[j]==0)
            {
                sum_mu[i*prime[j]]=0LL;
                break;
            }
            sum_mu[i*prime[j]]=-sum_mu[i];
        }
    }
    for(long long i=1LL;i<=N;i++)
        sum_mu[i]=(sum_mu[i-1]+((((i*i)%MOD)*sum_mu[i])%MOD))%MOD;
}

long long solve(long long n,long long m)
{
    long long ret=0LL,last;
    if(n>m)
        swap(n,m);
    for(long long d=1LL;d<=n;d=last+1)
    {
        last=min(n/(n/d),m/(m/d));
        ret=(ret+((sum(d,last)*f(n/d,m/d))%MOD))%MOD;
    }
    return ret;
}

long long f(long long x,long long y)
{
    if(x>y)
        swap(x,y);
    long long ret=0LL,last,tmp;
    for(long long k=1LL;k<=x;k=last+1LL)
    {
        last=min(x/(x/k),y/(y/k));
        tmp=(((((x/k)*(x/k+1LL))>>1LL)%MOD)
        *((((y/k)*(y/k+1LL))>>1LL)%MOD))%MOD;
        ret=(ret+(((sum_mu[last]-sum_mu[k-1]+MOD)%MOD)*tmp)%MOD)%MOD;
    }
    return ret;
}

long long sum(long long a,long long b)
{
    long long ret;
    ret=(((a+b)*(b-a+1LL))>>1LL)%MOD;
    return ret;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值