hdu 3480 Division (四边形不等式优化DP)

解决一个数学问题,通过贪心算法将数值分配到不同集合中,以使每个集合的最大与最小值差的平方之和最小。使用动态规划及四边形不等式优化算法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

题目描述

传送门

题目大意:将n个数划分到m个集合中,每个集合的代价是集合中最大元素与最小元素差的平方。求划分的最小代价。

题解

这个问题可以贪心的想,必然是权值接近的分成一个集合。
那么我们只要把权值排序,问题就又变成了划分问题。
f[j][i]=min{f[k][i1]+(val[j]val[k+1])(val[j]val[k+1])}
然后一如既往的用四边形不等式优化。。。。

代码

#include<iostream>
#include<algorithm>
#include<cstring>
#include<cstdio>
#define LL long long 
#define inf 1000000000
using namespace std;
int val[10003],dp[10003][5003],s[10003][5003];
int n,m,T;
int pow(int x)
{
    return x*x;
}
int main()
{
    freopen("a.in","r",stdin);
    scanf("%d",&T);
    for (int t=1;t<=T;t++) {
       scanf("%d%d",&n,&m);
       for (int i=1;i<=n;i++) scanf("%d",&val[i]);
       sort(val+1,val+n+1);
       //for (int i=1;i<=n;i++) cout<<val[i]<<" ";
       //cout<<endl;
       memset(dp,0,sizeof(dp));
       for (int i=1;i<=n;i++) 
        dp[i][1]=pow(val[i]-val[1]),s[i][1]=0;
       for (int i=2;i<=m;i++) {
          s[n+1][i]=n;
          for (int j=n;j>i;j--) {
            dp[j][i]=inf;    
            for (int k=s[j][i-1];k<=s[j+1][i];k++) {
               int tmp=dp[k][i-1]+pow(val[j]-val[k+1]);
               if (tmp<dp[j][i]) 
                dp[j][i]=tmp,s[j][i]=k;
            }
          }
       }
       printf("Case %d: %d\n",t,dp[n][m]);
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值