首先,这道题不可能直接算n!和a^k而后暴力解法,数太大了。那就乖乖找规律吧。
以输入n=6,a = 10,为例。
6! =
,
10 =
,
若是6!能够被10^k整除,那么6!的素因数必定包含10的素因数,那么k就 =6!与10的相同素因数中,个数最少的那个素因数的个数。
6!与10的相同素因数有2和5,6!中2的数量是4个,5的数量是1个,故此例的k = 1。
以n=10,a=10为例再看一遍:
首先都分别筛选素因数
10! =
;
10 =
;
看到10!和素因数有2,3,5,7,是包含10的全部素因数2和5的,故能够整除,在2和5中,素因数2的个数为8个,素因数5的个数为2个,故k = 2。
晚上迷迷糊糊敲的,好多其实没必要要,懒得改了html
#include<iostream> #include<cstdio> #include<vector> #include<cmath> using namespace std; const int maxn = sqrt(1000)+1; typedef struct { int prime; int num;//对应素因数的个数,也就是幂指数 } primearray,*pa; void initial(vector<int>&prime)//用筛除法求出素数列表 { bool isPrime[maxn]; for(int i = 0; i<maxn; i++) { isPrime[i] = true; } isPrime[0] = false; isPrime[1] = false; for(int j = 2; j<maxn; j++) { if(!isPrime[j]) continue; prime.push_back(j); for(int k = j*j; k<maxn; k += j) { isPrime[k] = false; } } } vector<primearray> getpa(vector<int>&prime,int x)//求出一个数全部的素因数,用num存储对应素因数个数 { vector<primearray>pa; int len = prime.size(); for(int i = 0; i<len && prime[i] <= x; i++) { bool isprime = false; primearray pnode; pnode.num = 0; pnode.prime = prime[i]; while(x%pnode.prime == 0) { x /= pnode.prime; isprime = true; } if(isprime) pa.push_back(pnode); } return pa; } int main() { vector<int>prime; int n,a,k=0; while(scanf("%d%d",&n,&a) != EOF) { initial(prime); vector<primearray>pa = getpa(prime,a); int len = pa.size(); for(int i = 0;i<pa.size();i++) {//由于没法直接拿n!来用,太大了,就从n一点点开始找同一个素因数,n找完了,就找n-1,最后到1,累加获得此素因数的个数 int nn = n; while(nn>1) { int nt = nn; while( nt % pa[i].prime == 0) { nt /= pa[i].prime; pa[i].num++; } nn--; } } k = pa[0].num;//找出最小的num for(int j = 0;j<pa.size();j++) { if(pa[j].num == 0) break; int num = pa[j].num; if(k > pa[j].num) k = pa[j].num; } printf("%d\n",k); } return 0; }