1068. 环形石子合并 (环形,区间dp)

1068. 环形石子合并 (环形,区间dp)_第1张图片

原题链接- AcWing 

分析:与石子合并只加了一个环形的条件

对于环形问题,如果只是枚举中断点的话,在石子合并的基础上多开一维,时间复杂度是O(n^4)

可以采用一个普遍的方法,就是把环转换成一个链

1068. 环形石子合并 (环形,区间dp)_第2张图片 

 通过把从1展开的链接在n的后面,这样子枚举的时候枚举以 位置2 断开的链,只需要枚举 以2开始,长度为len的链,就可以枚举n与1相邻的情况了

状态转移方程基本和石子合并一样,不同点在于环的存在,导致循环枚举不同

for(int len=1;len<=n;len++)
        for(int l=1;l+len-1<=2*n;l++)
        {//由于模拟中间断点,把前面断开的接到数组后面去,所以最大可能枚举到2n

           ...
        }

 

#include 
#include 
#include 
using namespace std;
const int N=410;
int a[N];
int s[N];
int dp[N][N];
int g[N][N];

int main()
{
    int n;
    cin>>n;
    for(int i=1;i<=n;i++) cin>>a[i],a[n+i]=a[i];
    
    for(int i=1;i<=2*n;i++) s[i]=s[i-1]+a[i];
    
    memset(dp,0x3f,sizeof dp),memset(g,-0x3f,sizeof g);
    
    for(int len=1;len<=n;len++)
        for(int l=1;l+len-1<=2*n;l++)
        {
            int r=l+len-1;
            if(len==1) dp[l][r]=g[l][r]=0;
            else
                for(int k=l;k

你可能感兴趣的:(动态规划,动态规划,c++,算法)