CF888E Maximum Subsequence
Posted qyj060604
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了CF888E Maximum Subsequence相关的知识,希望对你有一定的参考价值。
CF888E Maximum Subsequence
有一种叫做折半搜索的好东西
我们把数列劈成两半,分别搜索,再合并
合并可以排序+二分或者排序+单调性
代码极短
#include<bits/stdc++.h> using namespace std; const int N=37; const int M=5000005; typedef long long ll; int n; ll m; ll a[N]; int mi; ll s1[M],s2[M]; int cnt1=0,cnt2=0; ll ans=0; ll llmax(ll x,ll y) return x>y?x:y; inline void dfs(int x,ll val,int t,int o) if(x==t) if(o==1) s1[++cnt1]=val; else s2[++cnt2]=val; return; dfs(x+1,val,t,o); dfs(x+1,(val+a[x+1])%m,t,o); inline int serch(int x) int l=1,r=cnt2,ans=0; s2[0]=0; while(l<=r) int mid=(l+r)>>1; if(s2[mid]<x) ans=mid,l=mid+1; r=mid-1; return s2[ans]; inline bool cmp(ll x,ll y) return x<y; int main() scanf("%d%d",&n,&m); mi=n/2; for(int i=1;i<=n;i++) scanf("%lld",&a[i]),a[i]%=m; dfs(0,0,mi,1); dfs(mi,0,n,2); for(int i=1;i<=cnt1;i++) ans=llmax(ans,s1[i]); for(int i=1;i<=cnt2;i++) ans=llmax(ans,s2[i]); sort(s1+1,s1+cnt1+1,cmp); sort(s2+1,s2+cnt2+1,cmp); int j=cnt2; s2[0]=0; for(int i=1;i<=cnt1;i++) ans=llmax(ans,(s1[i]+s2[cnt2])%m); while(j>0&&s2[j]>=m-s1[i]) j--; ans=llmax(ans,(s1[i]+s2[j])%m); printf("%lld\n",ans); return 0;
以上是关于CF888E Maximum Subsequence的主要内容,如果未能解决你的问题,请参考以下文章
CF888E Maximum Subsequence-折半搜索
CF888E Maximum Subsequence (折半枚举+ two-pointers)
Codeforces 888E:Maximum Subsequence(枚举,二分)