Codevs_2102_石子归并2_(划分型动态规划)

Posted 晴歌。

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Codevs_2102_石子归并2_(划分型动态规划)相关的知识,希望对你有一定的参考价值。

描述


http://codevs.cn/problem/2102/

2102 石子归并 2

 

时间限制: 10 s
空间限制: 256000 KB
题目等级 : 黄金 Gold
 
 
 
 
 
题目描述 Description

在一个园形操场的四周摆放N堆石子,现要将石子有次序地合并成一堆.规定每次只能选相邻的2堆合并成新的一堆,并将新的一堆的石子数,记为该次合并的得分。
试设计出1个算法,计算出将N堆石子合并成1堆的最小得分和最大得分.

输入描述 Input Description

数据的第1行试正整数N,1≤N≤100,表示有N堆石子.第2行有N个数,分别表示每堆石子的个数.

输出描述 Output Description

输出共2行,第1行为最小得分,第2行为最大得分.

样例输入 Sample Input

4
4 4 5 9

样例输出 Sample Output

43
54

数据范围及提示 Data Size & Hint

经典的区间动态规划。

分析


枚举起点即可.

 1 #include <bits/stdc++.h>
 2 using namespace std;
 3 
 4 const int maxn=100+5,INF=0x7fffffff;
 5 
 6 int n,ans1,ans2;
 7 int s[maxn<<1],dp1[maxn][maxn],dp2[maxn][maxn];
 8 
 9 void solve(){
10     ans1=INF, ans2=-INF;
11     for(int q=1;q<=n;q++){
12         for(int r=2;r<=n;r++)
13             for(int i=q;i<=q+n-r;i++){
14                 int j=i+r-1;
15                 dp1[i-q+1][j-q+1]=INF; dp2[i-q+1][j-q+1]=-INF;
16                 for(int k=i;k<j;k++){
17                     dp1[i-q+1][j-q+1]=min(dp1[i-q+1][j-q+1],dp1[i-q+1][k-q+1]+dp1[k+1-q+1][j-q+1]+s[j]-s[i-1]);
18                     dp2[i-q+1][j-q+1]=max(dp2[i-q+1][j-q+1],dp2[i-q+1][k-q+1]+dp2[k+1-q+1][j-q+1]+s[j]-s[i-1]);
19                 }
20             }
21         ans1=min(dp1[1][n],ans1);
22         ans2=max(dp2[1][n],ans2);
23     }
24     printf("%d\\n%d\\n",ans1,ans2);
25 }
26 void init(){
27     scanf("%d",&n);
28     for(int i=1;i<=n;i++){
29         int t; scanf("%d",&t);
30         s[i]=s[i-1]+t;
31     }
32     for(int i=n+1;i<=n*2;i++) s[i]=s[i-n]+s[n];
33 }
34 int main(){
35     init();
36     solve();
37     return 0;
38 }
View Code

 

以上是关于Codevs_2102_石子归并2_(划分型动态规划)的主要内容,如果未能解决你的问题,请参考以下文章

codevs 2102 石子归并2

2102 石子归并 2codevs

codevs——2102 石子归并 2(区间DP)

Codevs_1040_[NOIP2001]_统计单词个数_(划分型动态规划)

石子归并(codevs_1048)——区间dp

Codevs_1017_乘积最大_(划分型动态规划/记忆化搜索)