不要被阶乘吓倒

阶乘是个很有意思的函数,我们来看看两个跟阶乘相关的问题。

1、给定一个整数N,那么N的阶乘N!末尾有多少个0呢?例如:N=10,N! = 3628800,末尾就有两个0

2、求N! 的二进制表示中最低位1的位置

我们先分析第一个问题

我们发现0的个数,就是10的个数,而10是由2跟5组成的,但是,5的个数明显少于2,所以问题就转换为求5的个数。


 1 #include <iostream>
2 using namespace std;
3 // O(nlogn),思路:找0的个数,就是找10的个数,就是2*5的个数,2比5多,所以就是找5的个数,首先找到5的倍数,再判断这些数里面有多少个5
4 int numOfZeros1(int n)
5 {
6 //i从1开始,当n为26时,那么i就是1,2,3,4,5
7 //j就是5*i,所以对于的j就是5,10,15,20,25,第二个while循环找的就是j中有多少个5,像数字25,就有2个5
8 //count表示的5的个数,即0的个数
9 int i, j, count;
10 i = 1;
11 count = 0;
12 while (5 * i <= n)
13 {
14 j = 5 * i;
15 while (j % 5 == 0)
16 {
17 count++;
18 j = j / 5;
19 }
20 i++;
21 }
22 return count;
23 }
24 // o(logn),从时间复杂度上来说,优化的多。思路:n=26时,0的个数就是[26/25]+[26/5]=1+5=6
25 int numOfZeros2(int n)
26 {
27 int i, count;
28 i = 0;
29 count = 0;
30 while (n / 5)
31 {
32 count += n / 5;
33 n /= 5;
34 }
35 return count;
36 }
37 int main()
38 {
39 int n;
40 n = 125;
41 //test
42 cout<<numOfZeros1(n)<<endl;
43 cout<<numOfZeros1(n)<<endl;
44 system("pause");
45 return 0;
46 }

不要被阶乘吓倒,布布扣,bubuko.com

时间: 2024-10-10 16:07:52

不要被阶乘吓倒的相关文章

第2章 数字之魅——不要被阶乘吓倒

不要被阶乘吓倒 问题描述 阶乘(Factorial)是个很有意思的函数,但是不少人都比较怕它,我们来看看两个与阶乘相关的问题: 问题1. 给定一个整数N,那么N的阶乘N!末尾有多少个0呢?例如:N=10,N!=3 628 800,N!的末尾有两个0. 问题2. 求N!的二进制表示中最低位1的位置. 分析与解法 有些人碰到这样的题目会想:是不是要完整计算出N!的值?如果溢出怎么办?事实上,如果我们从"哪些数相乘能得到10"这个角度来考虑,问题就变得简单了. 首先考虑,如果N!= K×10

编程之美2.2 不要被阶乘吓倒

开始看到这道题目的时候,我还以为是利用字符串表示整型数的思想,后来一看,由于是一个数的阶乘,那么,如果这个数本身就很大,那么,即使是利用字符串表示也是不合理的,所以,看了下这道题的解释,书中给出了一个公式之后就明白了题目的意思. 首先,我先把函数声明和题目要求贴出来: /*2.2 不要被阶乘吓倒*/ /*2.2.1 N!的末尾有多少个0*/ int DutCountOf0InFactorialN(int); /*2.2.2 N!的二进制表示中最低位1的位置*/ int DutPositionOf

【编程之美】目录

第1章  游戏之乐——游戏中碰到的题目 1.1 让CPU占用率听你的指挥 1.2 中国象棋将帅问题 1.3 一摞烙饼的排序 1.4 买书问题 第2章  数字之魅——数字中的技巧 2.1 求二进制中1的个数 2.2 不要被阶乘吓倒 2.3 寻找发帖"水王" 2.4 1的数目 2.5 寻找最大的K个数 2.6 精确表达浮点数 2.7 最大公约数问题 2.8 找符合条件的整数 2.9 斐波那契(Fibonacci)数列 2.10 寻找数组中的最大值和最小值 2.11 寻找最近点对 2.12

《编程之美》笔记

第1章 游戏之乐----游戏中碰到的题目 第2章 数学之魅----数字中的技巧 2.2 不要被阶乘吓倒 问题2:求N!的二进制表示中最低位1的位置. 方法一:一个数字k如果乘以2,则其二进制就会左移一位.那么N!的质因子分解中的2的个数就是N!的二进制中有多少个后缀零.具体实现与N!后缀零一样. 1 int lowestOne(int N) 2 { 3 int ans=0; 4 while(N) 5 { 6 N>>=1; 7 ans+=N; 8 } 9 return ans+1;//由于求的是

算法-计算阶乘n!末尾0的个数

算法逻辑转载自计算阶乘n!末尾0的个数: 问题描述    给定参数n(n为正整数),请计算n的阶乘n!末尾所含有"0"的个数.    例如,5!=120,其末尾所含有的"0"的个数为1:10!= 3628800,其末尾所含有的"0"的个数为2:20!= 2432902008176640000,其末尾所含有的"0"的个数为4. 计算公式    这里先给出其计算公式,后面给出推导过程.    令f(x)表示正整数x末尾所含有的&q

1003 阶乘后面0的数量

1003 阶乘后面0的数量 基准时间限制:1 秒 空间限制:131072 KB 分值: 5 难度:1级算法题 n的阶乘后面有多少个0? 6的阶乘 = 1*2*3*4*5*6 = 720,720后面有1个0. Input 一个数N(1 <= N <= 10^9) Output 输出0的数量 Input示例 5 Output示例 1其实只要循环除五就可以找到规律,其实也可以证明出来. 1 #include <iostream> 2 #include <cstdio> 3 #

高精度运算-阶乘累积求和

# include <stdio.h> # include <math.h> # define N 66 int main(){ int s[N] = {0}, a[N] = {0};// s累加和,a累积求阶乘 int i,j,k,n,digit=1; //digit代表的是数字的位数 scanf("%d",&n); a[0]=1; s[0]=1; if(n==1)// 如果是1,阶乘和就是1,直接输出 printf("%d",s[

关于阶乘

描述:给定两个数n,m,其中m是一个素数. 将n(0<=n<=2^31)的阶乘分解质因数,求其中有多少个m. 注:^为求幂符号. 输入: 第一行是一个整数s(0<s<=100),表示测试数据的组数 随后的s行, 每行有两个整数n,m. 输出: 输出m的个数 样例输入 3 100 5 16 2 1000000000 13 样例输出 24 15 83333329 当n,m体量很小的时候,用这个代码就可以AC: 1 #include <iostream> 2 using na

XDU1019 阶乘因子的个数

题意是让你求一个最小的N, 使得N!有M个0,N的阶乘中2的因子是远多于5的因子的个数, 因此我们统计出5的个数就知道其后面有几个0,对于一个数mid, mid!中5的因子的个数为mid/5 + mid/25 + mid/5^3 + ... 可以发现mid越大mid!中的5的个数越多, 因此我们可以二分答案, 代码如下: #include <cstdio> #include <cstring> #include <algorithm> #include <iost