题目
思路 优先队列/小根堆
先存后排,先把ans置为1,每次分别把ans的2、3、5倍存入优先队列,取出次数为n时,ans就是答案。要注意去重,每次循环的最后,把结果与ans相等的数据取出来。还要注意数据越界,要用long来存。
代码
class Solution {
public:
int nthUglyNumber(int n) {
priority_queue<long, vector<long>, greater<long>> pq;
long ans = 1;
for(int i = 1; i < n ; i++){
pq.push(ans * 2);
pq.push(ans * 3);
pq.push(ans * 5);
ans = pq.top();
pq.pop();
while(!pq.empty() && pq.top() == ans)
pq.pop();
}
return ans;
}
};
思路 动态规划
先排后存,用三指针表示2、3、5乘这个数得到的结果正准备添加到dp数组中。
代码
class Solution {
public:
int nthUglyNumber(int n) {
vector<int> dp(n + 1);
dp[1] = 1;
int p1 = 1, p2 = 1, p3 = 1;
for(int i = 2; i <= n; i++){
int minn = min(min(dp[p1] * 2, dp[p2] * 3), dp[p3] * 5);
dp[i] = minn;
if(minn == dp[p1] * 2) p1++;
if(minn == dp[p2] * 3) p2++;
if(minn == dp[p3] * 5) p3++;
}
return dp[n];
}
};