題目連結:
hdu:http://acm.hdu.edu.cn/showproblem.php?pid=5265
bc(中文):http://bestcoder.hdu.edu.cn/contests/contest_chineseproblem.php?cid=599&pid=1002
題意:
從n個數中取兩個數A,B,使得(A+B)%p最大。
題解:
首先對所有的數先取一次模,那麼則有0<=a[i]+a[j]<=2*p-2(i!=j),對于a[i]+a[j]>=p的,隻要使a[i],a[j]都最大即可求出最大的(a[i]+a[j])%p,因為a[i]+a[j]不可能超過2*p了。而對于a[i]+a[j]<p的那些,我們固定a[i],二分去找j,使得a[i]+a[j]<p且j盡可能大即可。
代碼:
1 #include<iostream>
2 #include<cstdio>
3 #include<cstring>
4 #include<algorithm>
5 using namespace std;
6 typedef long long LL;
7
8 const int maxn=1e5+10;
9
10 int n,p;
11 LL a[maxn];
12
13 int main(){
14 while(scanf("%d%d",&n,&p)==2&&n){
15 for(int i=0;i<n;i++){
16 scanf("%lld",a+i);
17 a[i]%=p;
18 }
19 sort(a,a+n);
20 LL ans=(a[n-1]+a[n-2])%p;
21 for(int i=0;i<n-1;i++){
22 LL tmp=a[i];
23 int lef=i+1,rig=n;
24 while(lef<rig){
25 int mid=lef+(rig-lef)/2;
26 if(tmp+a[mid]<p){
27 if(tmp+a[mid]>ans) ans=tmp+a[mid];
28 lef=mid+1;
29 }else{
30 rig=mid;
31 }
32 }
33 }
34 printf("%lld\n",ans);
35 }
36 return 0;
37 }
38 /*
39 4 5
40 1 2 3 4
41 */