一个环上有n个点,价值 a[i],现在要选择m个点,
其中连续段的第一个元素的价值不算,求总和最大?
先考虑一条链
f[i][j][0/1] ,j 是目前选择了的点的个数, 0/1 当前点i 是否选择
状态转移:
f[i][j][0]=max(f[i-1][j][0],f[i-1][j][1])
f[i][j][1]=max(f[i-1][j-1][0],f[i-1][j-1][1]+a[i])
现在考虑环的问题
这题发现只有 n 和 1 的位置要多考虑一下,因为n的取法会影响1
我们考虑 元素n是否选择 ,对应dp的边界设置
// f[1][0][0]=f[1][1][1]=0
// f[1][0][0]=0, f[1][1][1]=a[1]
#include <iostream>
#include <cstring>
using namespace std;
const int N=4000;
int n,m,a[N],f[N][N][2];
void solve(){
int i,j;
cin>>n>>m;
for(i=1;i<=n;i++) cin>>a[i];
int ans=-1e9;
memset(f,-127,sizeof f);
f[1][0][0]=f[1][1][1]=0;
for(i=2;i<=n;i++)
for(j=0;j<=m&&j<=i;j++){
f[i][j][0] =max(f[i-1][j][0],f[i-1][j][1]);
f[i][j][1] =max(f[i-1][j-1][1]+a[i],f[i-1][j-1][0]);
}
ans=max(ans,f[n][m][0]);
memset(f,-127,sizeof f);
f[1][0][0]=0,f[1][1][1]=a[1];
for(i=2;i<=n;i++)
for(j=0;j<=m&&j<=i;j++){
f[i][j][0] =max(f[i-1][j][0],f[i-1][j][1]);
f[i][j][1] =max(f[i-1][j-1][1]+a[i],f[i-1][j-1][0]);
}
ans=max(ans,f[n][m][1]);
cout<<ans<<endl;
}
signed main(){
int cas; cin>>cas;
while(cas--) solve();
}
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 单线程的Redis速度为什么快?
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 展开说说关于C#中ORM框架的用法!