LintCode 4.丑数 II

设计一个算法,找出只含素因子2,3,5 的第 n 大的数。

符合条件的数如:1, 2, 3, 4, 5, 6, 8, 9, 10, 12…

注意事项

我们可以认为1也是一个丑数

样例 如果n = 9, 返回 10

思路:

由题目的要求可知:找到出 2, 3, 5倍数的数。并排序。直到到第n个数

定义一个数组存放丑数,1是已知的丑数。
从2,3,5中挑选最小的添加到数组中

选择num[0]*2,num[0]*3,num[0]*5中最小的数为新的丑数,显然应该选择2,即num[1] = 2;
然后再从num[1]*2,num[0]*3,num[0]*5中进行选择,显然选择3,即num[2] = 3;
然后再从num[1]*2,num[1]*3,num[0]*5中选择最小的,选择2,即num[3] = 4,依次进行如下操作,

得到丑数后,在相应的丑数因子计数器上+1 以便于寻找下一个更大的丑数(数组中的丑数和因子构成新的丑数),
如果不更新,就不会产生新的丑数。

下一个丑数 = 之前生成的丑数数组中寻找一个 * (2 or 3 or 5)
在原有的数组中寻找新的丑数,因为2,3,5的(2,3,5)倍数也必然是丑数

public static int getMin(int num1, int num2, int num3){
        //获得最小的值
        int temp = num1 < num2 ? num1 : num2;
            return temp < num3 ? temp : num3;
    }
    public int nthUglyNumber(int n) {
        // write your code here
        int[] ugly = new int[n];
        ugly[0] = 1;    //已知1为丑数

        int num2 = 0;   //定义因子计数器
        int num3 = 0;
        int num5 = 0;

        for(int i = 1 ; i //新丑数是 2,3,5倍数中最小
            ugly[i] =  getMin(ugly[num2]* 2, ugly[num3] *3, ugly[num5] * 5);
            //判断新存放的丑数是2,3,5哪个数的倍数
            //并在相应的倍数对应计数器+1,使得与因子相乘的数值变化,得到新的丑数
            if(ugly[i] == ugly[num2] * 2)
                num2++;
            if(ugly[i] == ugly[num3] * 3)
                num3++;
            if(ugly[i] == ugly[num5] * 5)
                num5++;
        }
        return ugly[n-1];
    }

你可能感兴趣的:(LintCode笔记,lintcode,丑数,Java)