题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3480

Time Limit: 10000/5000 MS (Java/Others) Memory Limit: 999999/400000 K (Java/Others)

Little D is really interested in the theorem of sets recently. There’s a problem that confused him a long time.   
Let T be a set of integers. Let the MIN be the minimum integer in T and MAX be the maximum, then the cost of set T if defined as (MAX – MIN)^2. Now given an integer set S, we want to find out M subsets S1, S2, …, SM of S, such that 
and the total cost of each subset is minimal.

Input

The input contains multiple test cases. 
In the first line of the input there’s an integer T which is the number of test cases. Then the description of T test cases will be given. 
For any test case, the first line contains two integers N (≤ 10,000) and M (≤ 5,000). N is the number of elements in S (may be duplicated). M is the number of subsets that we want to get. In the next line, there will be N integers giving set S.

Output

For each test case, output one line containing exactly one integer, the minimal total cost. Take a look at the sample output for format.

Sample Input

2
3 2
1 2 4
4 2
4 7 10 1

Sample Output

Case 1: 1
Case 2: 18

题意:

给出含有N元素的集合S,选取M个S的子集,要求满足SU S2 U … U SM = S;

定义一个集合的最大元素为MAX,最小元素为MIN,它的花费为(MAX - MIN)2,现要求所有子集的总花费最少为多少。

题解:

先将S内元素从小到大排列,然后将这N个元素的序列分成M组(因为若有重叠元素,必然会使得花费增加);

那么假设dp[i][j]为前i个数分成j组的最小花费,那么求出dp[N][M]即可回答问题;

状态转移方程为dp[i][j] = min{ dp[k][j-1] + (S[i] - S[k+1])2 },j-1≤k<i;

那么当j固定时,计算dp[i][j]时需要枚举k,若k可能取值到a,b两点,且j-1≤a<b<i,

若有 dp[b][j-1] + (S[i] - S[b+1])2 ≤ dp[a][j-1] + (S[i] - S[a+1])2,则b点优于a点;

将上式变形,得到:

b点优于a点 <=> 

再然后就是斜率优化的老套路了(斜率优化的详情查看斜率DP分类里之前的文章),就不再赘述。

AC代码:

#include<bits/stdc++.h>
using namespace std;
const int maxn=+; int n,m,S[maxn];
int dp[maxn][maxn];
int q[maxn],head,tail; int up(int a,int b,int j) //g(a,b)的分子部分
{
return (dp[b][j-]+S[b+]*S[b+])-(dp[a][j-]+S[a+]*S[a+]);
}
int down(int a,int b) //g(a,b)的分母部分
{
return *S[b+]-*S[a+];
} int main()
{
int t;
scanf("%d",&t);
for(int kase=;kase<=t;kase++)
{
scanf("%d%d",&n,&m);
for(int i=;i<=n;i++) scanf("%d",&S[i]);
sort(S+,S+n+); for(int i=;i<=n;i++) dp[i][]=(S[i]-S[])*(S[i]-S[]);
for(int j=;j<=m;j++)
{
head=tail=;
q[tail++]=j-;
for(int i=j;i<=n;i++)
{
while(head+<tail)
{
int a=q[head], b=q[head+];
if(up(a,b,j)<=S[i]*down(a,b)) head++; //g(a,b)<=S[i]
else break;
}
int k=q[head];
dp[i][j]=dp[k][j-]+(S[i]-S[k+])*(S[i]-S[k+]); while(head+<tail)
{
int a=q[tail-], b=q[tail-];
if(up(a,b,j)*down(b,i)>=up(b,i,j)*down(a,b)) tail--; //g(a,b)>=g(b,i)
else break;
}
q[tail++]=i;
}
} printf("Case %d: %d\n",kase,dp[n][m]);
}
}

注意DP边界的初始化。

HDU 3480 - Division - [斜率DP]的更多相关文章

  1. hdu 3480 Division(斜率优化DP)

    题目链接:hdu 3480 Division 题意: 给你一个有n个数的集合S,现在让你选出m个子集合,使这m个子集合并起来为S,并且每个集合的(max-min)2 之和要最小. 题解: 运用贪心的思 ...

  2. HDU 2829 - Lawrence - [斜率DP]

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2829 T. E. Lawrence was a controversial figure during ...

  3. ACM-ICPC 2016 沈阳赛区现场赛 I. The Elder && HDU 5956(斜率DP)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5956 题意:一颗树上每条边有个权值,每个节点都有新闻要送到根节点就是1节点,运送过程中如果不换青蛙就是 ...

  4. HDU 3480 Division(斜率DP裸题)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3480 题目大意:将n个数字分成m段,每段价值为(该段最大值-该段最小值)^2,求最小的总价值. 解题思 ...

  5. HDU 3480 Division(斜率优化+二维DP)

    Division Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 999999/400000 K (Java/Others) Tota ...

  6. HDU 3480 Division DP斜率优化

    解题思路 第一步显然是将原数组排序嘛--然后分成一些不相交的子集,这样显然最小.重点是怎么分. 首先,我们写出一个最暴力的\(DP\): 我们令$F[ i ][ j ] $ 为到第\(i\)位,分成\ ...

  7. HDU 3480 division

    题目大意:一个有n个数的集合,现在要求将他分成m+1个子集,对子集i设si表示该集合中最大数与最小数的差的平方.求所有si的和的最小值.n<=10000,m<=5000. 分析:最优解的m ...

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

    Problem Description Little D is really interested in the theorem of sets recently. There’s a problem ...

  9. hdu 2829 Lawrence(斜率优化DP)

    题目链接:hdu 2829 Lawrence 题意: 在一条直线型的铁路上,每个站点有各自的权重num[i],每一段铁路(边)的权重(题目上说是战略价值什么的好像)是能经过这条边的所有站点的乘积之和. ...

随机推荐

  1. [RN] 04 - React Navigation

    react-navigation和react-router的对比: 支持的平台: react-navigation: react-native react-router: react-native.r ...

  2. 详解js中的apply与call的用法

    前言 call 和 apply 都是为了改变某个函数运行时的 context 即上下文而存在的,换句话说,就是为了改变函数体内部 this 的指向.call 和 apply二者的作用完全一样,只是接受 ...

  3. SQL Compare数据库比较工具 完全破解+使用教程

    来源http://www.cnblogs.com/duci/articles/4482665.html 一.使用教程 SQL Compare是编程人员常用的比较两个数据库之间差异的工具.可以用来比较数 ...

  4. Eclipse------新建文件时没有JSP File解决方法

    1.为没有web选项的eclipse添加web and JavaEE插件 .在Eclipse中菜单help选项中选择install new software选项 .在work with 栏中输入 Ju ...

  5. 【Python】Docx解析

    1.cd D:\ProgramData\Anaconda3 2.pip install python-docx 3.python代码处理 # -*- coding: utf-8 -*- import ...

  6. java.lang.IllegalArgumentException: No converter found for return value of type

    原文地址: http://blog.csdn.net/linhaiguo/article/details/51554766 问题原因: 请求返回的数据无法转换,需要添加如下配置 解决方法: 1.在po ...

  7. osg使用shader动态修改纹理坐标

    #include <osg/Node> #include <osg/Geometry> #include <osg/Notify> #include <osg ...

  8. MQTT_DEMO

    1 /* 2 Copyright (c) 2009-2012 Roger Light <roger@atchoo.org> 3 All rights reserved. 4 5 Redis ...

  9. QT显示中文 连接上文

    1.首先是建立Linux开发环境1.1.在windowsXP下安装博创公司提供的虚拟机软件VMware Workstation,版本为VMware-workstation-full-7.0.1-227 ...

  10. C++ template —— 表达式模板(十)

    表达式模板解决的问题是:对于一个数值数组类,它需要为基于整个数组对象的数值操作提供支持,如对数组求和或放大: Array<), y(); ... x = 1.2 * x + x * y; 对效率 ...