/* 返回顶部 */

Luogu P2424 约数和

gate

题意:f(n)表示n的约数的和。给定x,y,求f(x)+f(x+1)+...+f(y)。

暴力枚举显然不行。

枚举一个数的约数会有很多重复的,考虑改为求1~n的倍数

(n/i)表示1~n中i的倍数的个数(i,2i,3i...(n/i)i)

即 f(n) = Sum((n/i)*i) (i=1~n)

那么答案即为f(y)-f(x-1)

复杂度$O(y)$,继续优化

比如f(8) = 8*1 + 4*2 + 2*3 + 2*4 + 1*5 + 1*6 + 1*7 + 1*8

发现(n/i)的部分有很多重复的,i又可以写成等差数列的形式

所以把重复的用区间表示

设区间[l,r]内,n/i的值相等。

初始l=1,每次l=上一个r+1;

满足倍数有n/i个的最大的数是n/(n/i),

即r = n/(n/l)

i的部分写成等差数列,即(r-l+1)*(l+r)/2

得f(n) = Sum( (n/l)*(r-l+1)*(l+r)/2 ) (r<=n)

 

代码如下

#include<cstdio>
#include<iostream>
#include<cmath>
#include<cstring>
#define MogeKo qwq
using namespace std;

long long x,y;

long long sum(long long n){
    long long l,r,ans = 0;
    for(l = 1;l <= n;l = r+1){
        r = n/(n/l);
        ans += (n/l)*(r-l+1)*(l+r)/2;
    }
    return ans;
}

int main(){
    scanf("%lld%lld",&x,&y);
    printf("%lld",sum(y)-sum(x-1));
    return 0;
}
View Code

 

posted @ 2019-11-07 23:20  Mogeko  阅读(95)  评论(0编辑  收藏  举报