题目描述
把只包含质因子2、3和5的数称作丑数(Ugly Number)。例如6、8都是丑数,但14不是,因为它包含质因子7。 习惯上我们把1当做是第一个丑数。求按从小到大的顺序的第N个丑数。
示例1
输入
7
返回值
8
使用常规思路会导致超时:
class Solution { public: int GetUglyNumber_Solution(int index) { if(index<=0) return 0; int count = 1; int i = 1; while(count<index){ i++; if(isUglyNum(i)){ count++; } } return i; } bool isUglyNum(int n){ while(n != 1 && n%2 == 0){ n /= 2; } while(n != 1 && n%3 == 0){ n /= 3; } while(n != 1&& n%5 == 0){ n /= 5; } if(n == 1) return true; else return false; } };
利用三个队列进行存储:
class Solution { public: int GetUglyNumber_Solution(int index) { if(index<=0) return 0; queue<int> queue2; queue<int> queue3; queue<int> queue5; vector<int> array; array.push_back(1); int i = 0; while(i+1<index){ queue2.push(2*array[i]); queue3.push(3*array[i]); queue5.push(5*array[i]); if(queue2.front()<=queue3.front() && queue2.front()<=queue5.front()){ array.push_back(queue2.front()); if(queue2.front()==queue3.front()) queue3.pop(); if(queue2.front()==queue5.front()) queue5.pop(); queue2.pop(); } else if(queue3.front()<=queue2.front() && queue3.front()<=queue5.front()){ array.push_back(queue3.front()); if(queue3.front()==queue2.front()) queue2.pop(); if(queue3.front()==queue5.front()) queue5.pop(); queue3.pop(); } else{ array.push_back(queue5.front()); if(queue5.front()==queue2.front()) queue2.pop(); if(queue5.front()==queue3.front()) queue3.pop(); queue5.pop(); } i++; } int temp = array[i]; array.clear(); queue2.empty(); queue3.empty(); queue5.empty(); return array[i]; } };
使用一个数组和三个指针来实现:
class Solution { public: int GetUglyNumber_Solution(int index) { if(index<=0) return 0; int * array = new int[3*index+1]; array[0] = 1; int i = 0; //记录位置 int count = 1; //记录个数 int index1 = 1; int index2 = 2; int index3 = 3; int j = 1;//记录下一个要插入数据的位置 while(count<index){ array[j++] = array[i] * 2; array[j++] = array[i] * 3; array[j++] = array[i] * 5; if(array[index1]<=array[index2] && array[index1]<=array[index3]){ i = index1; if(array[index1]==array[index2]) index2 += 3; if(array[index1]==array[index3]) index3 += 3; index1 += 3; }else if(array[index2]<=array[index1] && array[index2]<=array[index3]){ i = index2; if(array[index2]==array[index3]) index3 += 3; index2 += 3; }else{ i = index3; index3 += 3; } count++; } int result = array[i]; delete array; return result; } };
使用空间更少的方式进行计算
public class Solution { public int GetUglyNumber_Solution(int index) { if(index<=0) return 0; int[] array = new int[index]; array[0] = 1; int nextIndex = 1; int index2=0; int index3=0; int index5=0; int min; while(nextIndex < index){ min = minNum(array[index2]*2,array[index3]*3,array[index5]*5); array[nextIndex++] = min; if(min == array[index2]*2) index2++; if(min == array[index3]*3) index3++; if(min == array[index5]*5) index5++; } return array[nextIndex-1]; } int minNum(int a,int b,int c){ int min = (a < b ? a:b); min = min < c ? min : c; return min; } }