CF1614D2 Divan and Kostomuksha (hard version)
重排数组
a(n\le 10^6,a_i\le 2\cdot 10^7) ,使\sum_{i=1}^n\gcd(a_1,a_2,...,a_i) 最大化,输出最大值。
这很像一个 DP。我们会发现随着
考虑如何计算
考虑如何优化
数论方面的复杂度我不会分析,请高人指点。
#include <bits/stdc++.h>
#define int long long
using namespace std;
const int N=1e5+5,M=2e7;
int n,m,ans,x,a[N],cnt[M+5],f[M+5],v[M+5],prime[M+5];
signed main(){
cin>>n;
for(int i=1;i<=n;i++){
cin>>a[i];
cnt[a[i]]++;
}
for(int i=2;i<=2e7;i++){
if(!v[i])prime[++m]=i;
for(int j=1;j<=m&&i*prime[j]<=2e7;j++){
v[i*prime[j]]=prime[j];
if(i%prime[j]==0)break;
}
}
for(int i=1;i<=m;i++)
for(int j=2e7/prime[i];j;j--)cnt[j]+=cnt[j*prime[i]];
for(int i=2e7;i;i--){
if(!cnt[i])continue;
f[i]=i*cnt[i];
for(int j=1;j<=m&&i*prime[j]<=2e7;j++)f[i]=max(f[i],f[i*prime[j]]+(cnt[i]-cnt[i*prime[j]])*i);
if(ans<f[i])ans=f[i],x=cnt[i];
}
cout<<ans+n-x;
}