006--求解500万以内的亲和数

题目描述:
求500万以内的所有亲和数
如果两个数a和b,a的所有真因数之和等于b,b的所有真因数之和等于a,则称a,b是一对亲和数。

例如220和284,1184和1210,2620和2924。

思路:利用数组记录从1-5,000,000

#include<stdio.h>  
  
int sum[5000010];   //为防越界  
  
int main()   
{  
    int i, j;  
    for (i = 0; i <= 5000000; i++)   
        sum[i] = 1;  //1是所有数的真因数所以全部置1  
      
    for (i = 2; i + i <= 5000000; i++)  //预处理,预处理是logN(调和级数)*N。  
        //@litaoye:调和级数1/2 + 1/3 + 1/4......的和近似为ln(n),  
        //因此O(n *(1/2 + 1/3 + 1/4......)) = O(n * ln(n)) = O(N*log(N))。  
    {    
        //5000000以下最大的真因数是不超过它的一半的  
        j = i + i;  //因为真因数,所以不能算本身,所以从它的2倍开始  
        while (j <= 5000000)   
        {    
            //将所有i的倍数的位置上加i  
            sum[j] += i;    
            j += i;       
        }  
    }  
      
    for (i = 220; i <= 5000000; i++)   //扫描,O(N)。  
    {  
        // 一次遍历,因为知道最小是220和284因此从220开始  
        if (sum[i] > i && sum[i] <= 5000000 && sum[sum[i]] == i)  
        {  
            //去重,不越界,满足亲和  
            printf("%d %d/n",i,sum[i]);  
        }  
    }  
    return 0;  
}  


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值