F(n) = (n % 1) + (n % 2) + (n % 3) + ...... (n % n)。其中%表示Mod,也就是余数。
例如F(6) = 6 % 1 + 6 % 2 + 6 % 3 + 6 % 4 + 6 % 5 + 6 % 6 = 0 + 0 + 0 + 2 + 1 + 0 = 3。
给出n,计算F(n), 由于结果很大,输出Mod 1000000007的结果即可。
Input
输入1个数N(2 <= N <= 10^12)。
Output
输出F(n) Mod 1000000007的结果。
Input示例
6
Output示例
3思路:余数成等差;时间复杂度sqrt(n); 用等差数列求和的时候有个除法,所以用了下逆元;
#include<iostream>
#include<cstdio>
#include<cmath>
#include<string>
#include<queue>
#include<algorithm>
#include<stack>
#include<cstring>
#include<vector>
#include<list>
#include<set>
#include<map>
using namespace std;
#define ll long long
#define mod 1000000007
#define inf 999999999
#define esp 0.00000000001
//#pragma comment(linker, "/STACK:102400000,102400000")
void extend_Euclid(ll a, ll b, ll &x, ll &y)
{
if(b == 0)
{
x = 1;
y = 0;
return;
}
extend_Euclid(b, a % b, x, y);
ll tmp = x;
x = y;
y = tmp - (a / b) * y;
}
ll mul(ll x,ll y)
{
x%=mod;
y%=mod;
return (x*y)%mod;
}
ll divi(ll x,ll y)
{
ll xx,yy;
extend_Euclid(y,mod,xx,yy);
xx=(xx%mod+mod)%mod;
return mul(x,xx);
}
int main()
{
ll x,y,z,i,t;
scanf("%lld",&z);
ll ans=0;
for(i=2;i<=z;i++)
{
if(z%i!=0)
{
ll d=z/i;
ll maxx=(z%i)/d+1;
d=-d;
ans+=mul((z%i),maxx)+divi(mul(maxx,mul((maxx-1),d)),2);
ans=(ans%mod+mod)%mod;
i+=maxx-1;
}
}
printf("%lld\n",ans);
return 0;
}
来源:https://www.cnblogs.com/jhz033/p/5499517.html