Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)
Total Submission(s): 2189    Accepted Submission(s): 1175

         本题其实很简单就是一个一个尝试就行,但是应该注意几点

第一:本题数据比较大,快速的求出素数表

第二:因为p/q<=1,所以p得取值范围应该是1<=p<=sqrt(n);

第三:运用二分查找迅速的查找当前的数是否是素数

第四:因为本题是求p,q 使得p*q最大,所以应该从最大往下搜for(j=m;j>=1;j--)。直到j<z位置不用再往下搜直接退出

代码:

1 #include<stdio.h>
2 #include<math.h>
3 #include<string.h>
4  int prim[100005],is[100005];
5  int num=0;
6 int find(int v)
7 {
8 int m;
9 int l=1,h=num;
10 while(l<h)
11 {
12 m=(l+h)/2;
13 if(prim[m]==v)
14 return 1;
15 if(prim[m]<v)
16 l=m+1;
17 else
18 h=m;
19 }
20 return 0;
21 }
22 int main()
23 {
24 int m,a,b,j,max,i,mark,boo[330],k,x,zx,zi,z;double t;
25 int s,e=(int)(sqrt(0.0+100000)+1);
26 memset(is,1,sizeof(is));
27 prim[++num]=2;is[0]=is[1]=0;
28 for(i=4;i<=100000;i+=2)
29 is[i]=0;
30 for(i=3;i<e;i+=2)
31 if(is[i])
32 {
33 prim[++num]=i;
34 for(s=i*2,j=i*i;j<=100000;j+=s)
35 is[j]=0;
36 }
37 for( ;i<100000;i+=2)
38 if(is[i])
39 prim[++num]=i;
40
41 while(scanf("%d%d%d",&m,&a,&b)!=EOF)
42 {
43 mark=0;z=0;
44 if(m==0 && a==0 && b==0)
45 break;
46 t=a*1.0/b;
47 for(j=m;j>=1;j--)
48 {
49 if(j<z)
50 break;
51 max=(int)sqrt(0.0+j);
52 for(i=max;i>=1;i--)
53 {
54 x=j/i;
55 if(x*t<=i && x>=i)
56 {
57 if(find(i)&&find(x))
58 {
59 if(x*i>z)
60 {
61 zx=x;
62 zi=i;
63 z=x*i;
64 }
65
66 }
67 }
68 }
69 }
70 printf("%d %d\n",zi,zx);
71 }
72 return 0;
73 }
74
75
76
77
78
79