http://acm.sdut.edu.cn/sdutoj/problem.php?action=showproblem&problemid=2169
感觉是有递归思想的 dp[j]表示从1到j分成了i段 最多分成m段 肯定是分的越多越小的 第一重循环为(1,m)
dp[j] = min(dp[j],dp[g]+pow(sum[g..j]);
#include <iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<stdlib.h>
#include<cmath>
using namespace std;
#define N 1010
#define INF 0xfffffff
#define LL long long
LL dp[];
LL sum[];
int a[];
int main()
{
int t,i,j,n,m,g;
cin>>t;
while(t--)
{
memset(sum,,sizeof(sum));
cin>>n>>m;
for(i = ; i <= n ; i++)
dp[i] = INF;
for(i = ; i <= n ; i++)
{
cin>>a[i];
sum[i] = sum[i-]+a[i];
dp[i] = sum[i]*sum[i];
}
for(i = ; i <= m ; i++)
{
for(j = n-m+i ; j >= i ; j--)
{
for(g = i- ; g < j ; g++)
dp[j] = min(dp[j],dp[g]+(sum[j]-sum[g])*(sum[j]-sum[g]));
}
}
cout<<dp[n]<<endl;
}
return ;
}