博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Project Euler 95:Amicable chains 亲和数链
阅读量:7091 次
发布时间:2019-06-28

本文共 3244 字,大约阅读时间需要 10 分钟。

The proper divisors of a number are all the divisors excluding the number itself. For example, the proper divisors of 28 are 1, 2, 4, 7, and 14. As the sum of these divisors is equal to 28, we call it a perfect number.

Interestingly the sum of the proper divisors of 220 is 284 and the sum of the proper divisors of 284 is 220, forming a chain of two numbers. For this reason, 220 and 284 are called an amicable pair.

Perhaps less well known are longer chains. For example, starting with 12496, we form a chain of five numbers:

12496 → 14288 → 15472 → 14536 → 14264 (→ 12496 → …)

Since this chain returns to its starting point, it is called an amicable chain.

Find the smallest member of the longest amicable chain with no element exceeding one million.


一个数除了本身之外的因数称为真因数。例如,28的真因数是1、2、4、7和14。这些真因数的和恰好为28,因此我们称28是完全数。

有趣的是,220的真因数之和是284,同时284的真因数之和是220,构成了一个长度为2的链,我们也称之为亲和数对。

有一些更长的序列并不太为人所知。例如,从12496出发,可以构成一个长度为5的链:

12496 → 14288 → 15472 → 14536 → 14264 (→ 12496 → …)

由于这条链最后又回到了起点,我们称之为亲和数链。

找出所有元素都不超过一百万的亲和数链中最长的那条,并给出其中最小的那个数。

解题

暴力应该可以的,直觉是简单的。如果对每个数求出其真因子的和,然后再求真因子和的真因子和,这样的时间复杂度很好,表示没有跑出来结果。然后发现这里的计算真因子的和的过程中重复的数很多的。所以可以先求出真因子的数的和,这样就是一个数组,下面的问题就是在数组中求第一个最长链的开始的值,这里开始没有理解对,以为是求最长链中许多数中的最小值那个,但是发现最长链的最小值就是其第一个值。还有上面也说了是求的第一个最长链,所以主要小于100万的最长链长度是28 有好多个的。

那么如何求亲和数链?

注意:

1.不是每个数有亲和数链的,如这个说的也是比较有意思的

问题还是如何找到链?

很显然的是我们发现 从a 开始的链会从 a结束,这个是有顺序要求的

可以发现,是亲和数链的时候不会出现环,这个很显然,但是也是解题的关键

所以发现环了就要结束

然后再判断结束时候的值和原始开始的值是否相等,相同求其长度。

JAVA

package Level3;import java.util.TreeSet;public class PE094{    public static void run2(){        int MAX = 1000000;        int[] next = new int[MAX];        // 真因数的和         for(int i=2;i
set = new TreeSet
(); for(int i=2+8;i
=MAX) break; // 记录最小值 subMIN = subMIN>j?j:subMIN; // 出现循环 结束 if(set.contains(j)==true) break; set.add(j); } if( j==i ){ // 这个的不好,在相同的长度时候 进行了更新 // longest = Math.max(set.size(), longest); // 记录长度最小的那个 这里在相同的长度时候只记录最小的 if(set.size() >longest){ longest = set.size(); MIN = subMIN; System.out.println(longest +" "+MIN + " "+ j); } } } System.out.println(longest +" "+MIN); } public static void main(String[] args) { long t0 = System.currentTimeMillis(); run2(); long t1 = System.currentTimeMillis(); long t = t1 - t0; System.out.println("running time="+t/1000+"s"+t%1000+"ms"); }}

结果

28  28  220  220  12496  12496  14316  14316  14316running time=2s415ms

 

第一个数是链的长度,链的最小值,链的第一个数

其实是比较多的,题目求的是第一个最长链,直接看题目容易误解。

在上面求真因数的和中,和的思想很类似,知道数的规律,进行求解。

Python 是直接在论坛中找到

# coding=gbkimport time as time def run():    MAX = 1000000    d = [1]*MAX     for i in xrange(2,MAX//2):        for j in xrange(2*i,MAX,i):            d[j]+=i     max_cl = 0    for i in xrange(2,MAX):        n,chain = i,[]        while d[n]
max_cl: max_cl,min_link = len(chain[k:]),min(chain[k:]) print min_link t0 = time.time()run() t1 = time.time()print "running time=",(t1-t0),"s"running time= 5.47899985313 s

 

转载地址:http://lanql.baihongyu.com/

你可能感兴趣的文章
杭州机场春运预计起降航班3.3万架次 国际和地区增开428架次
查看>>
菲律宾一座“慰安妇”少女像设置仅两天就被撤走
查看>>
美总统特朗普驳斥美媒涉通俄门报道:极具侮辱性
查看>>
[2]十道算法题【Java实现】
查看>>
深入React的生命周期(下):更新(Update)
查看>>
js实现栈
查看>>
前端必备,50 个 Chrome Developer Tools 必备技巧
查看>>
客户故事:4家银行如何打造新一代移动金融中心
查看>>
NDK开发中这些基本知识你都懂吗
查看>>
自动化运维工具ansible的实践
查看>>
一个22万张NSFW图片的鉴黄数据集?我有个大胆的想法……
查看>>
do 一下来了一个 redux
查看>>
Vue教程09:双向绑定对象中属性原理
查看>>
如何实现VM框架中的数据绑定
查看>>
关于this
查看>>
[译] 系列教程:选择准备安装的 TensorFlow 类型
查看>>
Webhook到底是个啥?
查看>>
Flutter学习 ---- TravisCI加持
查看>>
借用UAC完成的提权思路分享
查看>>
『中级篇』 Linux网络命名空间(25)
查看>>