LightOJ 1138(求末尾零个数)

来源:互联网 发布:java 项目中使用log4j 编辑:程序博客网 时间:2024/05/22 03:23

Description

You task is to find minimal natural number N, so that N! contains exactly Q zeroes on the trail in decimal notation. As you knowN! = 1*2*...*N. For example, 5! = 120, 120 contains one zero on the trail.

Input

Input starts with an integer T (≤ 10000), denoting the number of test cases.

Each case contains an integer Q (1 ≤ Q ≤ 108) in a line.

Output

For each case, print the case number and N. If no solution is found then print 'impossible'.

Sample Input

3

1

2

5

Sample Output

Case 1: 5

Case 2: 10

Case 3: impossible

不难发现,一个数一共包含了几个5,就会有几个零;比如,

5以及5之前的数一共包含了1个5,所以末尾共有1个零;

20以及20之前的数一共包含了4个5(5自身为1个,10包含一个,15包含一个,20包含一个),所以末尾共有4个零;

25以及25之前的数一共包含了6个5(5,10包含一个,15包含一个,20包含一个,25包含另个(5*5等于25,所以25包含两个)),所以末尾共有6个零;

28以及28之前的数一共包含了6个5,所以末尾共有6个零;

……
这样,我们只需要求出所要求的数n一共包含了几个5,然后在从0-500000000(因为Q最大是100000000,所以要查找的范围上限最大是500000000)中查找是否有一个数它所包含的5的个数等于n就行了,如果有等于n,那么输出查找到的这个数,如果没有,则输出不可能;
注意这里要用二分查找会减少时间复杂度避免超时;


#include<iostream>#include<cstdlib>#include<cstdio>#include<algorithm>#include<cstring>#include<map>#define inf 99999999#define mod 9973using namespace std;int tongji(int x)//统计当前数中5的个数{    int ans=0;    while(x)    {        ans+=x/5;        x=x/5;    }    return ans;}int serch(int n){    long long lower,upper,mid;    lower=1,upper=500000000;    while(lower<=upper)//二分查找    {        mid=(lower+upper)/2;         if(tongji(mid)<n)            lower=mid+1;         else            upper=mid-1;    }    if(tongji(lower)==n)//能找到,则返回查找到的那个值;        return lower;    else        return 0;}int main(){    int t;    int m;    int k=0;    scanf("%d",&t);    while(t--)    {        scanf("%d",&m);        if(serch(m)==0)            printf("Case %d: impossible\n",++k);        else            printf("Case %d: %d\n",++k,serch(m));    }    return 0;}


1 0
原创粉丝点击