zoukankan      html  css  js  c++  java
  • 洛谷P2388 阶乘之乘

    题目背景

    不告诉你……

    题目描述

    求出1!*2!*3!*4!*……*n!的末尾有几个零

    输入输出格式

    输入格式:

    n(n<=10^8)

    输出格式:

    有几个零

    输入输出样例

    输入样例#1: 复制
    10
    输出样例#1: 复制
    7


    首先末尾有0肯定就是乘10,10可以分解为2和5,显然2的数目多于5,于是就是统计5的数目

    然后可以转化一下,

    对于

    1
    1 2
    1 2 3
    1 2 3 4
    1 2 3 4 5
    1 2 3 4 5 6
    ……
    1 2 3 4 5 6 …… x

    我们来除一下5,发现能被5整除的项变成了:

    1
    1
    1
    1
    1
    1 2
    1 2
    1 2
    1 2
    1 2
    1 2 3
    1 2 3
    1 2 3
    1 2 3
    1 2 3
    ……
    1 2 3 4 5 …… x/5
    1 2 3 4 5 …… x/5
    1 2 3 4 5 …… x/5
    1 2 3 4 5 …… x/5
    1 2 3 4 5 …… x/5

    也就是5个
    1
    1 2
    1 2 3
    ……
    1 2 3 4 5 …… x/5

    这样就可以递归求解了

    另外,这次除5总共除掉了5+10+15+20+(n/5)*5个,可以用等差数列公式

    对于x应该是从5k+4开始的,多余的处理掉即可 时间复杂度O(logn)

     1 #include<cstdio>
     2 #include<cstdlib>
     3 #include<algorithm>
     4 #include<cstring>
     5 #define ll long long
     6 using namespace std;
     7 int n;
     8 ll work(int x){
     9     ll ret=0;
    10     for(int i=5;i<=x;i*=5){
    11         ret+=x/i;
    12     }
    13     return ret;
    14 }
    15 ll find(int x){
    16     if(x<5){
    17         return 0;
    18     }
    19     if(x<10){
    20         return (x-4);
    21     }
    22     ll ret=0;
    23     while((x+1)%5){
    24         ret+=work(x);
    25         x--;
    26     }
    27     ret+=1LL*5*(x/5)*(1+(x/5))/2;
    28     ret+=5*find(x/5);
    29     return ret;
    30 }
    31 int main()
    32 {
    33     scanf("%d",&n);
    34     printf("%lld
    ",find(n));
    35     return 0;
    36 }
  • 相关阅读:
    ENode 1.0
    ENode 1.0
    ENode 1.0
    canvas转图片
    Canvas API
    微信 js api[转]
    Dicom格式文件解析器[转]
    跟我学AngularJS:全局变量设置之value vs constant vs rootscope vs 服务[转]
    angularJS 事件广播与接收[转]
    RequireJs
  • 原文地址:https://www.cnblogs.com/w-h-h/p/7805321.html
Copyright © 2011-2022 走看看