LeetCode No.263 & No.264 Ugly Number I & II | #math

Q:

Write a program to check whether a given number is an ugly number.
Ugly numbers are positive numbers whose prime factors only include 2, 3, 5
. For example, 6, 8 are ugly while 14 is not ugly since it includes another prime factor 7. Note that 1 is typically treated as an ugly number.

A:

public class Solution {
    public static boolean isUgly(int num) {
        if (num <= 0)   { return false; }
        
        int[] divisors = {2, 3, 5};
        
        for(int i : divisors) {
            while (num % i == 0) {
                num /= i;
            }
        } 
        return num == 1;  //是1 true,不是1, false
    }
}

寻找第n个ugly number

int GetUglyNumber_Solution1(int n)
{
    if(n <= 0)
        return 0;

    int target_number = 0;
    int index = 0;   //ugly number founded, ++

    while(index < n)
    {
        ++target_number;

        if(isUgly(target_number))
        {
            ++index;
        }
    }
    return target_number;
}

Q:

Write a program to find the n-th ugly number. Ugly numbers are positive numbers whose prime factors only include 2, 3, 5. For example, 1, 2, 3, 4, 5, 6, 8, 9, 10, 12 is the sequence of the first 10 ugly numbers. Note that 1 is typically treated as an ugly number.

A:


public class Solution {
    public int nthUglyNumber(int n) {
        int[] ugly = new int[n];
        ugly[0] = 1;
        int index2 = 0, index3 = 0, index5 = 0;
        int factor2 = 2, factor3 = 3, factor5 = 5;
        for(int i=1;i<n;i++){
            int min = Math.min(Math.min(factor2,factor3),factor5);
            ugly[i] = min;
            if(factor2 == min)
                factor2 = 2*ugly[++index2];
            if(factor3 == min)
                factor3 = 3*ugly[++index3];
            if(factor5 == min)
                factor5 = 5*ugly[++index5];
        }
        return ugly[n-1];
    }
}

当用之前naive的做法时,每一个数进入的时候,从1到n(时间复杂度为O(n)),每一步都要进行module运算(本身带个for loop,时间复杂度为O(n)),总时间复杂度为O(n²)。

这些数字都是ugly number,因factor不同,被分成了三组:
(1) 1×2, 2×2, 3×2, 4×2, 5×2, …
(2) 1×3, 2×3, 3×3, 4×3, 5×3, …
(3) 1×5, 2×5, 3×5, 4×5, 5×5, …

也就是说,我们在找第n个ugly number的时候,merge这三组数,并且遍历他们。好处就是,已经算过的,就已经在数组里了,每一次next ungly number进来,都将会是目前最大的,比它小的ugly number在它之前,已经存好,不用再考虑了:


从另外一个角度说,每次我们对factor2,factor3,factor5运算完,比较的话,找的是三个值里最小的:

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容