区间dp Simple AniPop
https://codeforces.com/gym/102878/problem/C
给定一个环,逐个删除它的所有元素。删除一个元素,若n>=2得到它与相邻左右元素乘积的价值,而n=1时只得到被删除元素的价值。求价值max
自己没想出来,面向题解且实现出错,记录如下:
状态设计:假设dp[i][j]为开区间(i,j)均被消除,但端点仍然保留的价值。其中,j=i与i+1都是0,j=i+n时情况特殊,dp[i][i+n]+a[i]为最后消去a[i]的方案的最大值(这一点有点跳跃,需要对倒数第二次消除脑内模拟)
技巧:化环成链,paste。
dp实现的时候要保证访问到的状态已经最优,所以这里先枚举长度,根据区间枚举左右端点,要保证全部覆盖。
若0<=i,j<=n,虽然paste后dp[i][j]和dp[i+n][j+n]一样,但是由于之后骑缝的情况中需要调用,所以一样要记录。
代码如下:
#include<cstdio>
#include<iostream>
#include<algorithm>
using namespace std;
int a[1010],dp[1010][1010];
int main(){
int n,res;
scanf("%d",&n);
for(int i=1;i<=n;i++){
scanf("%d",&a[i]);
a[i+n]=a[i];
//res=a[i];
}
for(int l=1;l<=n;l++)
for(int i=1;l+i<=2*n;i++)
{
int j=l+i;
//int mx=max(a[i],a[j]),mn=min(a[i],a[j]);
for(int k=i+1;k<=j-1;k++)
dp[i][j]=max(dp[i][j],dp[i][k]+dp[k][j]+a[k]*a[i]*a[j]);
if(j==i+n)
res=max(dp[i][j]+a[i],res);
}
printf("%d\n",res);
return 0;
}

浙公网安备 33010602011771号