幂和阶乘 (Again Prime?No time.,UVa 10780)

 1 #include <iostream>
 2 #include <string.h>
 3 #include <string>
 4 #include <fstream>
 5 #include <algorithm>
 6 #include <stdio.h>
 7 #include <vector>
 8 #include <queue>
 9 #include <set>
10 #include <cmath>
11 using namespace std;
12 const double eps = 1e-8;
13 const int INF=0x7fffffff;
14 #define MAXN 10000007
15 typedef int LL;
16 int vis[MAXN];
17 int prime[700000];
18 
19 void sieve(int n)
20 {
21     int m=(int)sqrt(n+0.5);
22     memset(vis,0,sizeof(vis));
23     for(int i=2;i<=m;i++)if(!vis[i])
24     for(int j=i*i;j<=n;j+=i)vis[j]=1;
25 }
26 
27 int gen_prime(int n)
28 {
29     sieve(n);
30     int c=0;
31     for(int i=2;i<=n;i++)if(!vis[i])
32         prime[c++]=i;
33     return c;
34 }
35 
36 LL gcd(LL a,LL b)
37 {
38     return b==0?a:gcd(b,a%b);
39 }
40 
41 int d[10007][1300];
42 int main()
43 {
44     int N=gen_prime(10007);
45     memset(d,0,sizeof(d));
46     for(int i=2;i<=10000;i++)
47     {
48         int temp=i;
49         for(int j=0;j<N;j++)
50         while(temp!=1&&temp%prime[j]==0){temp/=prime[j];d[i][j]++;}
51         for(int j=0;j<N;j++)d[i][j]+=d[i-1][j];
52     }
53     int T,t=1;
54     int n,m;
55     scanf("%d",&T);
56     while(T--)
57     {
58         scanf("%d%d",&m,&n);
59         int ans=INF;
60         for(int i=0;i<N;i++){
61             int temp=m,tempn=0;
62             while(temp%prime[i]==0){tempn++;temp/=prime[i];}
63             if(tempn)ans=min(ans,d[n][i]/tempn);
64         }
65 
66 
67         printf("Case %d:\n",t++);
68         if(ans==0)printf("Impossible to divide\n");
69         else printf("%d\n",ans);
70     }
71     return 0;
72 }

预处理 d[n][m]  n!所含有prime[m]的个数

posted @ 2013-07-21 16:12  TO_Asia  阅读(741)  评论(0编辑  收藏  举报