AcWing 62 丑数
2019-03-13 21:15
239 查看
题目描述:
我们把只包含因子2、3和5的数称作丑数(Ugly Number)。
例如6、8都是丑数,但14不是,因为它包含因子7。
求第n个丑数的值。
样例
[code]输入:5 输出:5
注意:习惯上我们把1当做第一个丑数。
分析:
方法一:
打表备查,将每个已经判断的丑数保存进哈希表,如果某数能被2,3,5之一整除且商为丑数,则该数为丑数。该方法缺点是内存消耗太大,超过了限制。如果在判断丑数的函数里返回m[n/2]之类的,空间会超过限制,如果返回count函数,时间也会超过限制,所以仅限于几百个以内的丑数的判断
[code]class Solution { public: unordered_map<int,int> m; int getUglyNumber(int n) { int i,cnt = 0; for(i = 1;i < 6;i++){ m[i] = 1; cnt++; if(cnt == n) return i; } while(1){ if(judge(i)) m[i]++,cnt++; if(cnt == n) return i; i++; } } bool judge(int n){ if(n % 2 == 0) return m[n / 2]; if(n % 3 == 0) return m[n / 3]; if(n % 5 == 0) return m[n / 5]; return false; } };
方法二:
三指针法。先说下用的较少的vector的定义。
如果不提前定义vector的元素个数,之后会每次容量倍增的方式来拓展空间。
我们知道,丑数除了1一定是2,3,5的倍数,那么2的n倍,3的n倍,5的n倍也就是丑数的全集了。第一个丑数为1,那么接下的丑数就是1的2,3倍,1的二倍加入后,指针应该后移移到2,2的2被小于1的五倍,所以3之后还是要放进4.可能描述比较模糊,具体过程参考代码即可,类似于三路归并排序,从2,3,5的倍数组成的三个序列中每次挑出新的最小元素加入。
分析下过程:
向量q中,初始为1,先加入2,i++,再加入3,j++,加入4,i++,加入5,k++,加入6,i++,j++。可以看到,当加入的数是几个因子的倍数时,对应的指针都会++。
[code]class Solution { public: int getUglyNumber(int n) { vector<int> q(1,1); int i = 0,j = 0,k = 0; while(--n){ int t = min(q[i]*2,min(q[j]*3,q[k]*5)); q.push_back(t); if(q[i] * 2 == t) i++; if(q[j] * 3 == t) j++; if(q[k] * 5 == t) k++; } return q.back(); } };
相关文章推荐
- AcWing 76 和为S的连续正数序列
- AcWing 77 翻转单词顺序
- AcWing 109 天才ACM
- AcWing 78 左旋转字符串
- AcWing 110 防晒
- AC日记——丑数 codevs 1246
- AcWing 79 滑动窗口的最大值
- AcWing 111 畜栏预定
- AcWing 63 字符串中第一个只出现一次的字符
- AcWing 82 圆圈中最后剩下的数字
- AcWing 114 国王游戏
- AcWing 64 字符流中第一个只出现一次的字符
- AcWing 83 股票的最大利润
- AcWing 65 数组中的逆序对
- AcWing 84 求1+2+…+n
- AcWing 66 两个链表的第一个公共结点
- AcWing 85 不用加减乘除做加法
- AcWing 67 数字在排序数组中出现的次数
- AcWing 86 构建乘积数组
- AcWing 87 把字符串转换成整数