【剑指Offer面试编程题】题目1214:丑数--九度OJ

把只包含因子2、3和5的数称作丑数(Ugly Number)。例如6、8都是丑数,但14不是,因为它包含因子7。
习惯上我们把1当做是第一个丑数。求按从小到大的顺序的第N个丑数。

输入:

输入包括一个整数N(1<=N<=1500)。

输出:

可能有多组测试数据,对于每组数据,
输出第N个丑数。

样例输入:

3

样例输出:

3

【解题思路】本题最直观的想法就是从1开始遍历,然后判断每一个数是否为丑数,但这样肯定是一种非常耗时间的做法,不可取。那么我们是否可用从丑数的特点出发呢,从另一个角度来思考问题,我们可以用2 3 5这三个数相乘来组成丑数,我们唯一需要确保的就是我们组成的丑数是按从小到大的关系出现的。我们可以想象一个丑数的出现是前面某一个丑数乘以2 /3 /5的结果,所以我们可以维护三个index,分别对应是2 3 5下一个应该相乘的数,然后依次去这三个数的最小值作为下一个丑数,并更新三个index。如此继续迭代。

AC  code:

#include <cstdio>
#include <vector>
#include <algorithm>
using namespace std;
 
void build(vector<int> &vec)
{
  int t2=1,t3=1,t5=1;
  int cnt=1;
  while(cnt<=1501)
  {
    int a=vec[t2]*2,b=vec[t3]*3,c=vec[t5]*5;
    int mine=min(min(a,b),c);
    vec.push_back(mine);
    while(a<=mine){++t2;a=vec[t2]*2;}
    while(b<=mine){++t3;b=vec[t3]*3;}
    while(c<=mine){++t5;c=vec[t5]*5;}
    ++cnt;   
  }
}
 
int main()
{
  int n;
  vector<int> vec;
  vec.push_back(0);
  vec.push_back(1);
  build(vec);
  while(scanf("%d",&n)!=EOF)
  {
    printf("%d
",vec[n]);
  }
  return 0;
}
/**************************************************************
    Problem: 1214
    User: huo_yao
    Language: C++
    Result: Accepted
    Time:10 ms
    Memory:1024 kb
****************************************************************/

题目链接:http://ac.jobdu.com/problem.php?pid=1214

九度-剑指Offer习题全套答案下载:http://download.csdn.net/detail/huoyaotl123/8276299



原文地址:https://www.cnblogs.com/huoyao/p/4248887.html