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