推了一下午,写又花了一晚上,XD,自己还是太菜了
【题目地址】
题意简述
单组询问,给定一个 n n n,求下面的式子的值在 m o d 1 0 9 + 7 {\rm mod}\ 10^9+7 mod 109+7意义下的值。
∑ i = 1 n ∑ j = 1 n σ 1 ( i j ) \sum_{i=1}^n\sum_{j=1}^n\sigma_1(ij) i=1∑nj=1∑nσ1(ij)
其中 σ 1 ( i ) \sigma_1(i) σ1(i)表示 i i i的约数和,例如 σ 1 ( 12 ) = 1 + 2 + 3 + 4 + 6 + 12 = 28 \sigma_1(12)=1+2+3+4+6+12=28 σ1(12)=1+2+3+4+6+12=28
我们按照[SDOI2015]约数个数和的套路先考虑如何转换 σ 1 ( i j ) \sigma_1(ij) σ1(ij),其实也可以考虑映射,所以可以写成如下形式:
σ 1 ( i j ) = ∑ x ∣ i ∑ y ∣ j [ g c d ( x , y ) = 1 ] x j y \sigma_1(ij)=\sum_{x|i}\sum_{y|j}[gcd(x,y)=1]\frac{xj}{y} σ1(ij)=x∣i∑y∣j∑[gcd(x,y)=1]yxj
简略证明:
同样,每个质因数直间互不影响,所以我们考虑,对于一个质因数 p p p,其中 p a ∣ i , p b ∣ j p^a|i,p^b|j pa∣i,pb∣j(这里和上面链接的那道题一样, i p a ⊥ p a , j p b ⊥ p b \frac{i}{p^a}\perp p^a,\frac{j}{p^b}\perp p^b pai⊥pa,pbj⊥pb),所以对于当 x = p 0 x=p^0 x=p0时, x j y \frac{xj}{y} yxj的 y y y中肯定含有 p 0 ∼ p b p^0\sim p^b p0∼pb,而 x j xj xj中也只含有 p 0 ∼ p b p^0\sim p^b p0∼pb(此时仅对于这一个质因数),所以此时可以将因子为 p 0 ∼ p b p^0\sim p^b p0∼pb的取完,而另一部分则是在 y = p 0 y=p^0 y=p0时, x i y \frac{xi}{y} yxi的 y = 1 y=1 y=1了,而 x i xi xi肯定含有 p b ∼ p a + b p^{b}\sim p^{a+b} pb∼pa+b,而算 p b p^b pb时,是在 x , y x,y x,y同时为 1 1 1的情况下,只会算一次,所以不用减去它。那么此时对于因子 p p p的所有情况就算完了,而每次计算的时候都是一个没有因子 p p p,一个有,所以要满足 g c d ( x , y ) = 1 gcd(x,y)=1 gcd(x,y)=1,将其应用到所有的质因子上,就可以得到上面的式子。
那么原式就可以转化成:
∑ i = 1 n ∑ j = 1 n ∑ x ∣ i ∑ y ∣ j [ g c d ( i , j ) = 1 ] x j y \sum_{i=1}^n\sum_{j=1}^n\sum_{x|i}\sum_{y|j}[gcd(i,j)=1]\frac{xj}{y} i=1∑nj=1∑nx∣i∑y∣j∑[gcd(i,j)=1]yxj
我们用莫比乌斯反演的套路将其进行变形:
∑ i = 1 n ∑ j = 1 n ∑ d = 1 n μ ( d ) ∑ x ∣ i ∑ y ∣ j x j y [ d ∣ g c d ( x , y ) ] ∑ d = 1 n μ ( d ) ∑ d ∣ x ∑ d ∣ y x y ∑ x ∣ i n ∑ y ∣ j n j ∑ d = 1 n μ ( d ) ∑ d ∣ x ∑ d ∣ y x y ∑ i = 1 ⌊ n x ⌋ ∑ j = 1 ⌊ n y ⌋ j y ∑ d = 1 n μ ( d ) ∑ d ∣ x ∑ d ∣ y x y ⌊ n x ⌋ y ∑ j = 1 ⌊ n y ⌋ j ∑ d = 1 n μ ( d ) ∑ d ∣ x ∑ d ∣ y x y ⌊ n x ⌋ y ⌊ n y ⌋ × ( ⌊ n y ⌋ + 1 ) 2 ∑ d = 1 n μ ( d ) ∑ d ∣ x ∑ d ∣ y x ⌊ n x ⌋ ⌊ n y ⌋ × ( ⌊ n y ⌋ + 1 ) 2 ∑ d = 1 n μ ( d ) ∑ d ∣ x x ⌊ n x ⌋ ∑ d ∣ y ⌊ n y ⌋ × ( ⌊ n y ⌋ + 1 ) 2 \sum_{i=1}^n\sum_{j=1}^n\sum_{d=1}^n\mu(d)\sum_{x|i}\sum_{y|j}\frac{xj}{y}[d|gcd(x,y)] \\\sum_{d=1}^n\mu(d)\sum_{d|x}\sum_{d|y}\frac{x}{y}\sum_{x|i}^n\sum_{y|j}^nj \\\sum_{d=1}^n\mu(d)\sum_{d|x}\sum_{d|y}\frac{x}{y}\sum_{i=1}^{\lfloor\frac{n}{x}\rfloor}\sum_{j=1}^{\lfloor\frac{n}{y}\rfloor}jy \\\sum_{d=1}^n\mu(d)\sum_{d|x}\sum_{d|y}\frac{x}{y}\left\lfloor\frac{n}{x}\right\rfloor y\sum_{j=1}^{\lfloor\frac{n}{y}\rfloor}j \\\sum_{d=1}^n\mu(d)\sum_{d|x}\sum_{d|y}\frac{x}{y}\left\lfloor\frac{n}{x}\right\rfloor y\frac{\lfloor\frac{n}{y}\rfloor\times(\lfloor\frac{n}{y}\rfloor+1)}{2} \\\sum_{d=1}^n\mu(d)\sum_{d|x}\sum_{d|y}x\left\lfloor\frac{n}{x}\right\rfloor \frac{\lfloor\frac{n}{y}\rfloor\times(\lfloor\frac{n}{y}\rfloor+1)}{2} \\\sum_{d=1}^n\mu(d)\sum_{d|x}x\left\lfloor\frac{n}{x}\right\rfloor\sum_{d|y} \frac{\lfloor\frac{n}{y}\rfloor\times(\lfloor\frac{n}{y}\rfloor+1)}{2} i=1∑nj=1∑nd=1∑nμ(d)x∣i∑y∣j∑yxj[d∣gcd(x,y)]d=1∑nμ(d)d∣x∑d∣y∑yxx∣i∑ny∣j∑njd=1∑nμ(d)d∣x∑d∣y∑yxi=1∑⌊xn⌋j=1∑⌊yn⌋jyd=1∑nμ(d)d∣x∑d∣y∑yx⌊xn⌋yj=1∑⌊yn⌋jd=1∑nμ(d)d∣x∑d∣y∑yx⌊xn⌋y2⌊yn⌋×(⌊yn⌋+1)d=1∑nμ(d)d∣x∑d∣y∑x⌊xn⌋2⌊yn⌋×(⌊yn⌋+1)d=1∑nμ(d)d∣x∑x⌊xn⌋d∣y∑2⌊yn⌋×(⌊yn⌋+1)
而此时我们看后面那一大坨,分开考虑:
∑ d ∣ x x ⌊ n x ⌋ = ∑ x = 1 ⌊ n d ⌋ x d ⌊ n x d ⌋ \sum_{d|x}x\left\lfloor\frac{n}{x}\right\rfloor=\sum_{x=1}^{\lfloor\frac{n}{d}\rfloor}xd\left\lfloor\frac{n}{xd}\right\rfloor d∣x∑x⌊xn⌋=x=1∑⌊dn⌋xd⌊xdn⌋
我们把那一个 d d d拿出去,然后令 f ( n ) = ∑ i = 1 n i ⌊ n i ⌋ f(n)=\sum\limits_{i=1}^ni\left\lfloor\frac{n}{i}\right\rfloor f(n)=i=1∑ni⌊in⌋,其实根据前面链接的经验,我们很容易知道:
f ( n ) = ∑ i = 1 n i ⌊ n i ⌋ = ∑ i = 1 n σ 1 ( i ) f(n)=\sum\limits_{i=1}^ni\left\lfloor\frac{n}{i}\right\rfloor=\sum_{i=1}^n\sigma_1(i) f(n)=i=1∑ni⌊in⌋=i=1∑nσ1(i)
证明:
首先可以看出每一个因子乘以出现次数,然后就是前面链接里的证明了。
对于另一个,我们同样转换:
∑ d ∣ y ⌊ n y ⌋ × ( ⌊ n y ⌋ + 1 ) 2 = ∑ y = 1 ⌊ n d ⌋ ⌊ n y d ⌋ × ( ⌊ n y d ⌋ + 1 ) 2 \sum_{d|y} \frac{\lfloor\frac{n}{y}\rfloor\times(\lfloor\frac{n}{y}\rfloor+1)}{2} \\=\sum_{y=1}^{\lfloor\frac{n}{d}\rfloor}\frac{\lfloor\frac{n}{yd}\rfloor\times(\lfloor\frac{n}{yd}\rfloor+1)}{2} d∣y∑2⌊yn⌋×(⌊yn⌋+1)=y=1∑⌊dn⌋2⌊ydn⌋×(⌊ydn⌋+1)
其实我们令 g ( n ) = ∑ i = 1 n i × ( i + 1 ) 2 g(n)=\sum_{i=1}^n\frac{i\times(i+1)}{2} g(n)=∑i=1n2i×(i+1),那么可以得到:
g ( n ) = ∑ i = 1 n ⌊ n i ⌋ × ( ⌊ n i ⌋ + 1 ) 2 = ∑ i = 1 n ∑ j = 1 ⌊ n i ⌋ j g(n)=\sum_{i=1}^n\frac{\lfloor\frac{n}{i}\rfloor\times(\lfloor\frac{n}{i}\rfloor+1)}{2}=\sum_{i=1}^n\sum_{j=1}^{\lfloor\frac{n}{i}\rfloor}j g(n)=i=1∑n2⌊in⌋×(⌊in⌋+1)=i=1∑nj=1∑⌊in⌋j
此时 j j j要有贡献,条件为 j ≤ ⌊ n i ⌋ j\leq\lfloor\frac{n}{i}\rfloor j≤⌊in⌋,我们将其变形可以得到:
j ≤ ⌊ n i ⌋ j ≤ n i i ≤ n j i ≤ ⌊ n j ⌋ j\leq\lfloor\frac{n}{i}\rfloor \\\ \\j\leq\frac{n}{i} \\\ \\i\leq\frac{n}{j} \\\ \\i\leq\lfloor\frac{n}{j}\rfloor j≤⌊in⌋ j≤in i≤jn i≤⌊jn⌋
所以我们改变枚举顺序,得到:
g
(
n
)
=
∑
j
=
1
n
j
∑
i
=
1
⌊
n
i
⌋
1
g
(
n
)
=
∑
i
=
1
n
i
⌊
n
i
⌋
=
f
(
n
)
g(n)=\sum_{j=1}^nj\sum_{i=1}^{\lfloor\frac{n}{i}\rfloor}1 \\ g(n)=\sum_{i=1}^ni\lfloor\frac{n}{i}\rfloor=f(n)
g(n)=j=1∑nji=1∑⌊in⌋1g(n)=i=1∑ni⌊in⌋=f(n)
所以原式变成了:
∑ d = 1 n μ ( d ) d ( f ( n d ) ) 2 \sum_{d=1}^n\mu(d)d\left(f(\frac{n}{d})\right)^2 d=1∑nμ(d)d(f(dn))2
此时我们需要用杜教筛筛 F ( n ) = μ ( n ) n F(n)=\mu(n)n F(n)=μ(n)n,我们令 G ( n ) = n G(n)=n G(n)=n,那么 F ⨂ G = 1 F\bigotimes G=1 F⨂G=1,所以直接套入杜教筛公式,得到:
S ( n ) = 1 − ∑ i = 2 n i S ( ⌊ n i ⌋ ) S(n)=1-\sum_{i=2}^niS(\lfloor\frac{n}{i}\rfloor) S(n)=1−i=2∑niS(⌊in⌋)
前面用杜教筛,后面预处理加 O ( n ) O(\sqrt n) O(n)的算即可,复杂度 O ( n 2 3 ) O(n^{\frac{2}{3}}) O(n32)
#include<map>
#include<cstdio>
#include<cstring>
#include<algorithm>
#pragma GCC optimize(2)
#define ll long long
using namespace std;
const ll Mod=1e9+7;
const int M=2e6+10,MAX=2e6;
ll n,m,inv_2,cnt;
ll prime[M],mu[M],F[M],B[M];
ll &Rec(ll x){
if(x<=MAX) return F[x];
else return B[n/x];
}
bool vis[M];
ll s[M],p[M],sum[M],bum[M];
ll &Rec2(ll x){
if(x<=MAX) return sum[x];
else return bum[n/x];
}//空间储存技巧
ll fpow(ll a,ll b){
ll res=1;
for(;b;b>>=1,a=(a*a)%Mod){
if(b&1)res=(res*a)%Mod;
}
return res;
}
void init(){
memset(bum,-1,sizeof(bum));
memset(B,-1,sizeof(B));
s[1]=mu[1]=1;inv_2=fpow(2,Mod-2);
for(int i=2;i<=MAX;i++){
if(!vis[i]){
prime[++cnt]=i;
s[i]=p[i]=1+i;
mu[i]=-1;
}
for(int j=1,v;j<=cnt&&i*prime[j]<=MAX;j++){
v=i*prime[j];
vis[v]=1;
if(!(i%prime[j])){
s[v]=s[i]/p[i]*(p[i]*prime[j]+1);
p[v]=p[i]*prime[j]+1;
break;
}
mu[v]=-mu[i];
s[v]=s[i]*s[prime[j]];
p[v]=1+prime[j];
}
}
for(int i=1;i<=MAX;i++){
sum[i]=(sum[i-1]+s[i]%Mod)%Mod;
F[i]=(F[i-1]+(i*mu[i])%Mod)%Mod;
if(F[i]<0)F[i]+=Mod;
}
}
ll S(ll x){if(x>=Mod)x%=Mod;return (x*(x+1)%Mod)*inv_2%Mod;}
ll Sarea(ll L,ll R){return ((S(R)-S(L-1))%Mod+Mod)%Mod;}
ll GetS(ll x){
ll &ans=Rec2(x);
if(ans!=-1) return ans;
ans=0;
for(ll i=1,j;i<=x;i=j+1){
j=(x/(x/i));
ans=(ans+Sarea(i,j)*(x/i)%Mod)%Mod;
}
return ans;
}
ll calc(ll x){
ll &ans=Rec(x);
if(ans!=-1) return ans;
ans=1;
for(ll i=2,j;i<=x;i=j+1){
j=(x/(x/i));
ans=(ans-Sarea(i,j)*calc(x/i)%Mod)%Mod;
}
if(ans<0)ans+=Mod;
return ans;
}
ll Carea(ll L,ll R){return ((calc(R)-calc(L-1))%Mod+Mod)%Mod;}
ll Sqr(ll a){return a*a%Mod;}
ll solve(ll x){
ll ans=0;
for(ll i=1,j;i<=x;i=j+1){
j=(x/(x/i));
ans=(ans+Carea(i,j)*Sqr(GetS(x/i))%Mod)%Mod;
}
return ans;
}
int main(){
init();
scanf("%lld",&n);
printf("%lld\n",solve(n));
return 0;
}
另外一种类似的推导方式【IN-orz%%%】
本文深入解析一道关于求解特定数学表达式的数论竞赛题,通过莫比乌斯反演和杜教筛算法,详细展示了从问题理解到算法实现的全过程。

382

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



