ssl2863 石子合併 dp練習

2021-08-13 15:23:44 字數 1240 閱讀 5094

description

在乙個操場上一排地擺放著n堆石子。現要將石子有次序地合併成一堆。規定每次只能選相鄰的2堆石子合併成新的一堆,並將新的一堆石子數記為該次合併的得分。請設計乙個程式,計算出將n堆石子合併成一堆的最小得分。

input

每組資料第1行為乙個正整數n(2<=n<=100),以下n行,每行乙個正整數,小於10000,分別表示第i堆石子的個數(1<=i<=n)。

output

對於每組資料輸出乙個正整數,即最小得分

sample input713

781621418

sample output

239解題過程

這道題老師講過所以很快就ok了(其實主要是看書),首先在書上找出求出動態轉移方程,我們可以用f[i][j]表示從i到j堆石頭的最優解。

然後用s[i][j]表示從i-j石子堆的和。優化一下可以用s[i]表示前i堆的和,讓後s[j]-s[i-1]就可以做到s[i][j]的效果。

在列舉乙個k表示從i-j的第k個開始分,就可以求出來了。

然後動態轉移方程:f[i][j]=min(f[i][j],f[i][k]+f[k+1][j]+s[j]-s[i-1])

**

#include

#include

#include

using namespace std;

int n,x,s[101],f[101][101];

int main()

memset(f,127/3,sizeof(f));//給f賦值乙個很大的數

for (int i=1;i<=n;i++) f[i][i]=0;//預處理

for (int i=n-1;i>=1;i--)//從n-1開始列舉頭

for (int j=i+1;j<=n;j++)//這樣列舉可以從少堆的開始列舉

for (int k=i;k<=j-1;k++)//列舉**點

f[i][j]=min(f[i][j],f[i][k]+f[k+1][j]+s[j]-s[i-1]);

//動態轉移方程

printf("%d\n",f[1][n]);//輸出從1-n堆最優解

}

SSL 2863合併石子

time limit 10000ms memory limit 256000k在乙個操場上一排地擺放著n堆石子。現要將石子有次序地合併成一堆。規定每次只能選相鄰的2堆石子合併成新的一堆,並將新的一堆石子數記為該次合併的得分。請設計乙個程式,計算出將n堆石子合併成一堆的最小得分。每組資料第1行為乙個正...

SSL 2863 合併石子 區間動態規劃

在乙個操場上一排地擺放著n堆石子。現要將石子有次序地合併成一堆。規定每次只能選相鄰的2堆石子合併成新的一堆,並將新的一堆石子數記為該次合併的得分。請設計乙個程式,計算出將n堆石子合併成一堆的最小得分。每組資料第1行為乙個正整數n 2 n 100 以下n行,每行乙個正整數,小於10000,分別表示第i...

SSL 1597 石子合併問題

description 在乙個圓形操場的四周擺放著n 堆石子。現要將石子有次序地合併成一堆。規定每次只能選相鄰的2 堆石子合併成新的一堆,並將新的一堆石子數記為該次合併的得分。試設計乙個演算法,計算出將n堆石子合併成一堆的最小得分和最大得分。程式設計任務 對於給定n堆石子,程式設計計算合併成一堆的最...