Humble Numbers
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 15013 Accepted Submission(s): 6525
Write a program to find and print the nth element in this sequence
1 2 3 4 11 12 13 21 22 23 100 1000 5842 0
The 1st humble number is 1. The 2nd humble number is 2. The 3rd humble number is 3. The 4th humble number is 4. The 11th humble number is 12. The 12th humble number is 14. The 13th humble number is 15. The 21st humble number is 28. The 22nd humble number is 30. The 23rd humble number is 32. The 100th humble number is 450. The 1000th humble number is 385875. The 5842nd humble number is 2000000000.
一个humble数指素数因子只有2,3 , 5, 7的数,比如1(也是), 2, 3, 4, 5, 6, 7, 8, 9, 10, 12, 14, 15, 16, 18, 20, 21, 24, 25...而11就不是,因为11是它的素数因子。
第N个Humble数肯定是前n-1个数中的一个与(2,3,5,7)的乘积。 f[n]=min(f[a]*2,f[b]*3,f[c]*4,f[d]*5), a=b=c=d=1初始化。
对于2 有 1*2=2 2*2=4 ,6,8 , 10, 12, 14.。。。。
对于3 有 1*3=3 2*3=6 , 9,12, 15,18, 21.。。。。
对于5 有 1*5=5 2*5=10 ,15 ,20,25, 30,35.。。。。
对于7 有 1*7=7 2*7=7 ,21 ,28,35, 42, 49.。。。。
最开始a=b=c=d=1,取最小值2,f[2]=2,min(2,3,5,7) ,下一次取值时,原来的2不能用了,该f[2]*2=4了,所以下次取的时候,取最小值3,min(4,3,5,7),所以说当对于2的计数从1开始,只要被采纳选作Humble数,及计数器+1,这里的计数器其实是指对于每个数(2,3,5,7),f[i]的下标的计数器,即f[2]*2=4,为什么用f[a]*2呢,其实计数器是a,f[2]肯定比f[1]大,下一次应该使用4去参与和其它三个数的竞争,比最小。所以对于2,3,5,7每个数来说,只要自己被采用,自己的计数器就+1,再以5为例,初值1*5=5,该值被f[i]采纳为humble数,则下一次参与竞选Humble数该从10(f[2]*5)开始。考虑到每次竞选Humble数的时候有两个数相等,则这两个数的计数器都+1. 感觉没有说清楚。还得自己理解理解。
再举个简单的例子来说吧:
比如 一个数组中的元素已经从大到小排好序 如 num[4]={1, 3, 5,7},
再给定一个数,比如 2,求2与数组中元素的乘积排序是什么样子的。
因为数组中已经排好序,所以第一个数乘以2肯定是最小的,最小的找到了,那么第二个数乘以2肯定是次小的,以此类推,第三个数乘以2肯定为次次小的,第四个数乘以2肯定为最大的。其中的第一二三四个数,就相当于f[1],f[2],f[3]。。。。
代码:
#include <iostream> #include <algorithm> using namespace std; int f[5843]; int min4(int a,int b,int c,int d) { int m=min(min(a,b),min(c,d)); return m; } int main() { int a,b,c,d; a=b=c=d=1; f[1]=1; for(int i=2;i<=5842;i++) { f[i]=min4(f[a]*2,f[b]*3,f[c]*5,f[d]*7); if(f[i]==f[a]*2) a++; if(f[i]==f[b]*3) b++; if(f[i]==f[c]*5) c++; if(f[i]==f[d]*7) d++; } int n; while(cin>>n&&n) { if(n%10==1&&n%100!=11) cout<<"The "<<n<<"st humble number is "<<f[n]<<"."<<endl; else if(n%10==2&&n%100!=12) cout<<"The "<<n<<"nd humble number is "<<f[n]<<"."<<endl; else if(n%10==3&&n%100!=13) cout<<"The "<<n<<"rd humble number is "<<f[n]<<"."<<endl; else cout<<"The "<<n<<"th humble number is "<<f[n]<<"."<<endl; } return 0; }