【剑指offer】73.丑数
总目录:
1.问题描述
把只包含质因子2、3和5的数称作丑数(Ugly Number)。例如6、8都是丑数,但14不是,因为它包含质因子7。 习惯上我们把1当做是第一个丑数。求按从小到大的顺序的第 n个丑数。
数据范围:0≤n≤2000
要求:空间复杂度 O(n), 时间复杂度 O(n)
2.问题分析
丑数的数学意义不明,按公式是(2^x)*(3^y)*(5^z)
已知f(0)~f(n-1)的情况下,如何获得f(n)?
可以将x、y、z看作3条腿,每次要往前迈一步时看用那条腿往前迈可以使里程最小,迈出之后该腿的步数+1。
每个数都应该有一次乘以2、乘以3、乘以5的机会。
3.代码实例
1 class Solution { 2 public: 3 int GetUglyNumber_Solution(int index) { 4 //1 2 3 4 5 6 8 5 if (index <= 6) 6 return index; // 加快程序输出 7 8 // 三个变量 后面有大作用! 9 int i2 = 0, i3 = 0, i5 = 0; 10 vector<int> res(index, 0); 11 res[0] = 1; // 第一个丑数为 1 12 13 for (int i = 1; i < index; i++) { 14 // 得到下一个丑数,三者中最小的 15 res[i] = min(res[i2] * 2, min(res[i3] * 3, res[i5] * 5)); 16 /*第一次是 2、3、5比较,得到最小的是2*/ 17 /*第二次是 4、3、5比较,为什么是4了呢?因为上次2已经乘了一次了,所以接下去可以放的丑数在4、3、5之间*/ 18 // 所以开头的三个指针就是来标记2 3 5 乘的次数的 19 if (res[i] == res[i2] * 2) 20 i2++; 21 if (res[i] == res[i3] * 3) 22 i3++; 23 if (res[i] == res[i5] * 5) 24 i5++; 25 } 26 return res[index - 1]; 27 } 28 };