题目:

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

思路:

1、逐个判断

逐个判断每个整数是不是丑数。根据丑数的定义,丑数只能被2,3,5整除,也就是说,如果一个数能被2整除,连续除以2,如果能被3整除,连续除以3,如果能被5整除,连续除以5,如果最后得到1,那么这个数就是丑数,否则就不是。

2、创建数组保存已经找到的丑数

第一种方法效率比较低,因为该方法对每个数无论是丑事还是非丑数,都进行了计算判断,这在一定程度上是浪费,有没有可能避免这种浪费呢?

根据丑数的定义,后面的丑数应该是前面丑数的2,3,5的倍数结果,因此我们可以创建一个数组,里面的数字是排好序的丑数,每一个丑数都是前面的丑数乘以2,3,5得到。

那么如何保证排序呢?假设当前数组中最大的丑数为M,我们把已有的每个丑数分别乘以2,3,5(实际上并不需要对每个丑数做乘积,只需每次保存上一次的位置即可),分别得到第一个乘以2后大于M的结果M2,第一个乘以3后大于M的结果M3,第一个乘以5后大于M的结果M5,那么下一个丑数就是M2,M3,M5的最小者。

代码:

1、逐个判断

bool isUgly(int n){
while(n%2==0)
n=n/2;
while(n%3==0)
n=n/3;
while(n%4==0)
n=n/5;
if(n==1)
return true;
return false;
} int getUglyNumber(int index){
if(index<=0)
return 0;
int number=1;
int count=0;
while(count<=index){
if(isUgly(number))
count++;
number++;
}
return number;
} class Solution {
public:
int GetUglyNumber_Solution(int index) {
if(index<=0)
return 0;
int count=0;
int number=0;
while(count<index){
++number;
if(isUgly(number))
count++;
}
return number;
} bool isUgly(int n){
while(n%2==0)
n=n/2;
while(n%3==0)
n=n/3;
while(n/5==0)
n=n/5;
return (n==1)?true:false;
}
};

2、只对丑数做操作

int min_3(int num1,int num2,int num3){
num1=(num1<num2)?num1:num2;
num1=(num1<num3)?num1:num3;
return num1;
} int getUglyNumber_1(int index){
if(index<=0)
return 0;
int *uglyNumbers=new int[index];
uglyNumbers[0]=1;
int nextIndex=1; int *index_2=uglyNumbers;
int *index_3=uglyNumbers;
int *index_5=uglyNumbers; while(nextIndex<index){
uglyNumbers[nextIndex]=min_3(*index_2*2,*index_3*3,*index_5*5);
while(*index_2*2<=uglyNumbers[nextIndex]) ++index_2;
while(*index_3*3<=uglyNumbers[nextIndex]) ++index_3;
while(*index_5*5<=uglyNumbers[nextIndex]) ++index_5;
++nextIndex;
} int ugly=uglyNumbers[index-1];
delete[] uglyNumbers;
return ugly;
}

在线测试OJ:

http://www.nowcoder.com/books/coding-interviews/6aa9e04fc3794f68acf8778237ba065b?rp=2

AC代码:

class Solution {
public:
int GetUglyNumber_Solution(int index) {
if(index<=0)
return 0;
int uglyNumbers[index];
uglyNumbers[0]=1;
int nextIndex=1;
int index_2=0;
int index_3=0;
int index_5=0; while(nextIndex<index){
uglyNumbers[nextIndex]=min_3(uglyNumbers[index_2]*2,uglyNumbers[index_3]*3,uglyNumbers[index_5]*5);
while(uglyNumbers[index_2]*2<=uglyNumbers[nextIndex]) ++index_2;
while(uglyNumbers[index_3]*3<=uglyNumbers[nextIndex]) ++index_3;
while(uglyNumbers[index_5]*5<=uglyNumbers[nextIndex]) ++index_5;
++nextIndex;
}
return uglyNumbers[index-1];
} int min_3(int num1,int num2,int num3){
num1=(num1<num2)?num1:num2;
num1=(num1<num3)?num1:num3;
return num1;
} };

  

(剑指Offer)面试题34:丑数的更多相关文章

  1. 剑指Offer:面试题34——丑数(java实现)

    问题描述: 把只包含因子2.3和5的数称作丑数(Ugly Number).例如6.8都是丑数,但14不是,因为它包含因子7. 习惯上我们把1当做是第一个丑数.求按从小到大的顺序的第N个丑数. 思路1: ...

  2. 剑指Offer - 九度1214 - 丑数

    剑指Offer - 九度1214 - 丑数2013-11-21 21:06 题目描述: 把只包含因子2.3和5的数称作丑数(Ugly Number).例如6.8都是丑数,但14不是,因为它包含因子7. ...

  3. 【剑指offer 面试题34】丑数

    只包含因子2.3.5的数称作丑数. #include <iostream> #include <vector> using namespace std; int GetUgly ...

  4. 剑指offer系列59---寻找丑数

    [题目]把只包含因子2.3和5的数称作丑数(Ugly Number). * 例如6.8都是丑数,但14不是,因为它包含因子7. 习惯上我们把1当做是第一个丑数.求按从小到大的顺序的第N个丑数. 解法一 ...

  5. 【剑指Offer】33、丑数

      题目描述:   把只包含质因子2.3和5的数称作丑数(Ugly Number).例如6.8都是丑数,但14不是,因为它包含质因子7. 习惯上我们把1当做是第一个丑数.求按从小到大的顺序的第N个丑数 ...

  6. 【剑指offer】q34:丑数

    题目要求第n个丑数.所以对于中间结果不须要保存. def Humble(index): curHum = 1 M2 = 2; M3 = 3; M5 = 5 while index > 1: cu ...

  7. 剑指offer(33)丑数

    题目描述 把只包含因子2.3和5的数称作丑数(Ugly Number).例如6.8都是丑数,但14不是,因为它包含因子7. 习惯上我们把1当做是第一个丑数.求按从小到大的顺序的第N个丑数. 题目分析 ...

  8. 剑指offer三十三之丑数

    一.题目 如果一个数的因子中,出去1和本身以外,质数因子只包含2.3和5,则把改数称作丑数(Ugly Number).例如6.8都是丑数,但14不是,因为它包含质数因子7. 习惯上我们把1当做是第一个 ...

  9. 剑指Offer——笔试题+知识点总结

    剑指Offer--笔试题+知识点总结 情景回顾 时间:2016.9.23 12:00-14:00 19:00-21:00 地点:山东省网络环境智能计算技术重点实验室 事件:笔试 注意事项:要有大局观, ...

  10. Leetcode - 剑指offer 面试题29:数组中出现次数超过一半的数字及其变形(腾讯2015秋招 编程题4)

    剑指offer 面试题29:数组中出现次数超过一半的数字 提交网址: http://www.nowcoder.com/practice/e8a1b01a2df14cb2b228b30ee6a92163 ...

随机推荐

  1. 正确理解 AsyncTask,Looper,Handler三者之间的关系(基于android 4.0)

    Looper 和Handler 是理解好AsyncTask的一个基础,我们可以先从这里开始,先给出一个主线程和子线程互相通信的例子. package com.example.loopertest; i ...

  2. OpenGL ES之GLSurfaceView学习一:介绍

    原文地址::http://120.132.134.205/cmdn/supesite/?uid-5358-action-viewspace-itemid-6527 GLSurfaceView是一个视图 ...

  3. linux中怎样从底部向上查看log文件

    对于一些很大的log文件,我们用more查看时会很费劲,没有办法直接跳到末尾再向前查看. 我们可以用less来解决,less查看一个文件时,可以使用类似vi的command命令,在command模式下 ...

  4. 【转】Undefined symbols for architecture i386:和"_OBJC_CLASS_$_xx", referenced from:问题解决方法

    多个人共同操作同一个项目或拷贝项目时,经常会出现类似这样的问题: Undefined symbols for architecture i386: "_OBJC_CLASS_$_xx文件名& ...

  5. centos ssh 乱码

    vim /etc/sysconfig/i18n 然后把里面的LANG="zh_CN.UTF-8"改成LANG="zh_CN.GB18030"

  6. 请教下 Yii 和 Ajax来验证用户名是否存在

    添加一个 Custom, Model页面: CustomForm中: public function rules() { // 使用ajax 校验数据 return array( array('nam ...

  7. 职业操盘手内部教材 z

    重 点抢筹区:   是主力机构在低位拉高建仓后的一个相当尴尬的区域!因为在这个区域,场外的绝大多数投资者不敢买,而场内持有的人却很想卖!所以会出现成片的卖盘挂单! 由于主力向上做的意图已经非常明显,所 ...

  8. Page 63-64 Exercises 2.3.7 -------Introduction to Software Testing (Paul Ammann and Jeff Offutt)

    Use the following method printPrimes() for question a-d below //Find and prints n prime integers pri ...

  9. 初识-----基于Socket的UDP和TCP编程及测试代码

    一.概述 TCP(传输控制协议)和UDP(用户数据报协议是网络体系结构TCP/IP模型中传输层一层中的两个不同的通信协议. TCP:传输控制协议,一种面向连接的协议,给用户进程提供可靠的全双工的字节流 ...

  10. TCP/IP 相关知识点与面试题集

    第一部分:TCP/IP相关知识点 对TCP/IP的整体认 链路层知识点 IP层知识点 运输层知识点 应用层知识点 (这些知识点都可以参考:http://www.cnblogs.com/newwy/p/ ...