DP as a precondition to the interval [] Energy necklace Luo Gu p1063

(Ran practice range DP, then drag it from morning afternoon qwq)

Energy necklace [link] title

This question is then also typical interval DP. Because it is a necklace, a ring so clearly, then we can follow the same consolidation stones, put a ring of n nodes has become an extension 2 * n-node chain. Note that the last node is then 2 * n = tail marking head mark of the first node;

Then follow the usual operating range of DP: enumeration interval length, where I is an enumeration of several energy bead polymerized together;

Enumeration then left point: while ensuring that the right end is not beyond the scope of the 2 * n;

Define a right end point: j = i + num-1;

Next enumeration break;

Enumeration more critical breakpoint, the breakpoint enumerated from i ~ j-1, (we do not know why we also do not understand a word repeated calculation f [i] [j] when time k = j)

转移方程:f[i][j]=max(f[i][j],f[i][k]+f[k+1][j]+head[i]*tail[k]*tail[j]);

Because this is the first stack of stones 1 ~ k is a merged stack, then k + 1 ~ j stones piled combined into a stack, i ~ j thus combined, the two beads is now:

,所以+head[i]*tail[k]*tail[j];

Then finally enumeration (enum equivalent to what point break), find the maximum value;

CODE:

#include<bits/stdc++.h>

using namespace std;

inline int read(){
    int ans=0;
    char last=' ',ch=getchar();
    while(ch>'9'||ch<'0') last=ch,ch=getchar();
    while(ch>='0'&&ch<='9') ans=(ans<<1)+(ans<<3)+ch-'0',ch=getchar();
    if(last=='-') ans=-ans;
    return ans;
}

int n;
int head[202],tail[202];
int f[202][202];

int main(){
    n=read();
    for(int i=1;i<=n;i++)
      head[i]=read(),head[i+n]=head[i];
    for(int i=1;i<=2*n-1;i++)
      tail[i]=head[i+1];
    tail[2*n]=head[1];
    
    for(int num=2;num<=n;num++){
        for(int i=1;i+num-1<=2*n;i++){
            int j=i+num-1;
            for(int k=i;k<=j-1;k++)
                f[i][j]=max(f[i][j],f[i][k]+f[k+1][j]+head[i]*tail[k]*tail[j]);
        }
    }
    int ans=0;
    for(int i=1;i<=n;i++) ans=max(ans,f[i][i+n-1]);
    cout<<ans<<endl;
    return 0;
}

end-

  

Guess you like

Origin www.cnblogs.com/zhuier-xquan/p/11114086.html
Recommended