LeetCode263/264/1201 Ugly Number Series

the definite of ugly number is: positive numbers whose prime factors only include 2, 3, 5.

LeetCode263: check if a number is ugly number or not.
Idea1: think of this as a tree, and starting from the root, we have three subnodes(dividend) to choose. if there is a way that ends with 1. then that is the path, and we find a way, so the input is an ugly number.
idea2:
the order of 2s and 3s and 5s is not important, so that means if we

class Solution {
    public boolean isUgly(int num) {
        int[] divs = new int[]{2,3,5};
        if (num > 0) {
            for (int div: divs) { //try each one
                while (num % div == 0) { //this idea is good! but also need to keep in mind of all the conner case
                    num /= div;
                    if (num == 1) return true;
                }
            }
        }
        
        return num == 1;
    }
}

LeetCode264: Write a program to find the n-th ugly number.
starting from 1.
idea: you will never guess the way to solve this problem: DP.
now, we know that n<1690, so it’s not that long.

class Solution {
    public int nthUglyNumber(int n) {
        int i = 0; //2x pointer
        int j = 0;//3x pointer
        int k = 0; //5x pointer
        
        int[] ugly = new int[1690]; //this problem says n < 1690
        ugly[0] = 1;
        
        if (n == 1) {
            return 1;
        }
        
        for (int t = 1; t<1690; t++) { //we use this, means we defaultly think n >=2
            int nextUgly = Math.min(Math.min(ugly[i] * 2, ugly[j] * 3), ugly[k] * 5);
            ugly[t] = nextUgly;
            
            //let's find out the nextUgly comes from,only move that pointer
            //which means, check that nextUgly is evolved from what pointer
            if (nextUgly == ugly[i] * 2) i++;
            if (nextUgly == ugly[j] * 3) j++;
            if (nextUgly == ugly[k] * 5) k++;
            
            if (t + 1 == n) {
                return ugly[t];
            }
            
        }
        return -1;
        
    }
    //how can we guarantee there is no duplicate one? we don't need to, becasue this "everytime choose the minimum one" can guarantee? how can we avoid 2*3 and 3*2 count as the sameone?
}

1201 Ugly Number3
now, Write a program to find the n-th ugly number.
but this time, we define ugly number as: positive integers which are divisible by a or b or c.
example:
Input: n = 3, a = 2, b = 3, c = 5
Output: 4
Explanation: The ugly numbers are 2, 3, 4, 5, 6, 8, 9, 10… The 3rd is 4.

what needs us to take extra attention is: 1 <= n, a, b, c <= 10^9.so the range of n is much larger than Ugly number2.

now, since n can be that big, it is not wise to initialize a dp array with that long.
and any linear method will be very slow, as we can imagine. so id there a way to make it faster? the answer is yes.
https://leetcode.com/problems/ugly-number-iii/discuss/387780/JavaC%2B%2B-Binary-Search-with-Venn-Diagram-Explain-Math-Formula

posted @ 2020-12-12 01:03  EvanMeetTheWorld  阅读(28)  评论(0)    收藏  举报