您的位置:首页 > 其它

PE 530

2016-03-26 22:19 260 查看
orz rzz

题目大意:设 f(n)=∑d|ngcd(d,nd)f(n) = \sum_{d|n}gcd(d,\frac{n}{d}),F(n)=∑ni=1f(i)F(n) = \sum_{i = 1}^{n}f(i),求F(1015)F(10^{15})的值

题解:F(n)=∑ni=1∑d|igcd(d,id)F(n) = \sum_{i = 1}^n\sum_{d|i}gcd(d,\frac{i}d)

=∑d∑nd2i=1∑d′|i[gcd(d′,id′)==1]= \sum_d\sum_{i=1}^{\frac{n}{d^2}}\sum_{d'|i}[gcd(d',\frac{i}{d'})==1]

=∑d∑d′dμ(d′)∑n(dd′)2i=1σ0(i)= \sum_d\sum_{d'}d\mu(d')\sum_{i=1}^{\frac{n}{(dd')^2}}\sigma_0(i)

=∑nd=1ϕ(d)∑nd2i=1σ0(i)= \sum_{d=1}^n\phi(d)\sum_{i=1}^{\frac{n}{d^2}}\sigma_0(i)

时间复杂度O(n√lnn)O(\sqrt{n}\ln n)

#include<iostream>
#include<algorithm>
#include<cstring>
#include<string>
#include<ctime>
#include<cmath>
#include<cstdlib>
#include<cstdio>
#define LL long long
using namespace std;

const LL n = 1000000000000000;

LL sigma(LL n)
{
LL ret = 0;
for (LL i = 1,j;i <= n;i = j + 1)
{
j = min(n / (n / i),n);
ret += (j - i + 1) * (n / i);
}
return ret;
}

LL phi(LL x)
{
LL ret = 1;
for (LL i = 2;i * i <= x;i ++)
if (x % i == 0)
{
ret *= i - 1;
for (x /= i;x % i == 0;ret *= i,x /= i);
}
if (x ^ 1) ret *= x - 1;
return ret;
}

int main()
{
LL ans = 0;
for (LL d = 1;d * d <= n;d ++)
ans += phi(d) * sigma(n / d / d);
cout << ans << endl;

return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: