题意
求解
f(n)=∑i=1n∑j=1n⌈ij⌉[(i,j)=1]
其中
[(i,j)=1]={1,gcd(i,j)=10,others
分析
=-=又一道公式推论神题。。解法和题解不同,是从网上找的结论,推论过程自行搜索吧。对于向下取整存在公式
g(n)=∑i=1n∑j=1n⌊ij⌋[(i,j)=1]
g(n)=∑i|nmu[ni](∑j=1id[j])
其中 mu[i] 为莫比乌斯函数, d[j] 表示数 j 约数的个数。
于是可以利用筛法求出
代码
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<queue>
using namespace std;
#define LL long long
#define MAXN 1001000
const int mod=1e9+7;
int mu[MAXN];
LL ans[MAXN];
LL d[MAXN];
int phi[MAXN];
void getPhi(){
for(int i=1;i<MAXN;++i)
phi[i]=i;
for(int i=2;i<MAXN;++i)
if(phi[i]==i)
for(int j=i;j<MAXN;j+=i)
phi[j]=phi[j]/i*(i-1);
}
void getMu(){
for(int i=1;i<MAXN;++i){
int target=i == 1?1:0;
int delta=target-mu[i];
mu[i]=delta;
for(int j=i+i;j<MAXN;j+=i)
mu[j]+=delta;
}
}
void init(){
getPhi();
getMu();
for(int i=1;i<MAXN;++i)
for(int j=i;j<MAXN;j+=i)
d[j]++;
for(int i=1;i<MAXN;++i)
d[i]=(d[i]+d[i-1])%mod;
for(int i=1;i<MAXN;++i)
for(int j=i;j<MAXN;j+=i)
ans[j]=(ans[j]+mu[j/i]*d[i])%mod;
for(int i=1;i<MAXN;++i)
ans[i]=(ans[i]+phi[i]-1)%mod;
for(int i=2;i<MAXN;++i)
ans[i]=(ans[i]+ans[i-1])%mod;
}
int main(){
init();
int n;
while(~scanf("%d",&n)){
printf("%d\n",ans[n]);
}
}