牛客网-剑指office-丑数

题目:把只包含质因子2、3和5的数称作丑数(Ugly Number)。例如6、8都是丑数,但14不是,因为它包含质因子7。 习惯上我们把1当做是第一个丑数。求按从小到大的顺序的第N个丑数。
思路:首先想到的是暴力解法,一个一个的判断是不是丑数,并用一个计数器统计是第几个丑数,但是该算法的时间效率很低,无法通过OJ。
之前的暴力解法之所以效率较低,很大程度上是因为不管一个数是不是丑数,我们都需要对它进行计算。
因此我们可以先列出前几个丑数
1, 2,3, 4, 5,6,8, 9, 10,12,15
我们可以发现丑数应该是前面丑数乘以2,3或者5的结果。我们可以建立一个数组,存储排好序的丑数,每次计算下一个丑数时,在之前丑数的基础上分别乘以2、3或者5,并选出比当前最大丑数大的丑数中,最小的一个,继续存入该数组中,直到找到第index个丑数。
事实上,没必要每次从头开始分别乘以2、3或者5,因为已有的丑数是按顺序存放在数组中的,必然存在一个位置t2上的数,在t2之前的数,乘以2小于已有的最大的丑数,在t2之后的数,乘以2大于已有的丑数,所以我们每次只需要记录下t2的位置,并不断更新即可。对于3和5,也存在同样的t3和t5.

class Solution {
public:
	int GetUglyNumber_Solution(int index) {
		if (index <= 0) return 0;
		vector<int> v;
		int t2 = 0, t3 = 0, t5 = 0;
		int m2, m3, m5;
		int nmax = 1;
		v.push_back(1);
		while (v.size() < index)
		{
			for (int i = t2; i < v.size(); ++i)
			{
				if ((v[i] * 2) > nmax)
				{
					m2 = v[i] * 2;
					t2 = i;
					break;
				}
			}
			for (int i = t3; i < v.size(); ++i)
			{
				if ((v[i] * 3) > nmax)
				{
					m3 = v[i] * 3;
					t3 = i;
					break;
				}
			}
			for (int i = t5; i < v.size(); ++i)
			{
				if ((v[i] * 5) > nmax)
				{
					m5 = v[i] * 5;
					t5 = i;
					break;
				}
			}
			nmax = min(m2, min(m3, m5));
			v.push_back(nmax);
		}
		return nmax;
	}
	
};

python的解法:

class Solution:
    def GetUglyNumber_Solution(self, index):
        if index <= 0:
            return 0
        t2 = 0
        t3 = 0
        t5 = 0
        nmax = 1
        v = [1]
        m2 = 0
        m3 = 0
        m5 = 0
        while len(v) < index:
            for i in range(t2, len(v)):
                if (v[i]*2) > nmax:
                    m2 = v[i]*2
                    t2 = i
                    break
            for i in range(t3, len(v)):
                if (v[i] * 3) > nmax:
                    m3 = v[i] * 3
                    t3 = i
                    break
            for i in range(t5, len(v)):
                if (v[i]*5) > nmax:
                    m5 = v[i]*5
                    t5 = i
                    break
            nmax = min(m2, m3, m5)
            v.append(nmax)
        return nmax

猜你喜欢

转载自blog.csdn.net/qq_43387999/article/details/90774203