HDU3507Print Article (斜率优化DP)
One day Zero want to print an article which has N words, and each word i has a cost Ci to be printed. Also, Zero know that print k words in one line will cost
M is a const number.
Now Zero want to know the minimum cost in order to arrange the article perfectly.
InputThere are many test cases. For each test case, There are two numbers N and M in the first line (0 ≤ n ≤ 500000, 0 ≤ M ≤ 1000). Then, there are N numbers in the next 2 to N + 1 lines. Input are terminated by EOF.OutputA single number, meaning the mininum cost to print the article.Sample Input
5 5
5
9
5
7
5
Sample Output
230
应该是初步get了,由于以前看到的博主的配图和用语有误,让人再混沌之中浮尸了好久,头疼,应该是这样的图。
wa,我自己画的,将就辣。

开始学的时候感觉好抽象啊,还特意去学了瞎‘凸包’专题,QwQ,这里主要是解释一下‘为什么’。
初学感悟:
零:我们把线段的两个端点叫做点对,把dp[j]+(sum[i]-sum[j])^2取得最小的是j叫做i的最优点。
一:一对点对里,前面的点和后面的点的优劣关系由sum i决定,但是删去前劣后优的点后,剩下的就是前由后劣,得到i时的队首最优。
Ω,本来的点对满足k=(y1-y2)/(x1-x2) > sum[i],由于sum i是递增的,后面这个不等关系可能会改变。即此时(i==n时)队首是最优点,但是当i>n时,可能存在k<sum[i],这也是为什么我们需要每个i维护队首元素,使得队首是最优点。
二:我们维护的是一个斜率上升的图形,1,2,3,4代表的是队列里的点,求dp i时有4步:
α, 对队首:斜率k(1,2)和sum i 的关系不再得到满足,说明对于i点,队首1已经不如队首2优,抛弃1,依此后推...
β, dp i= dp q[top]+...
γ, 对队尾:具体的如果我们要加入一点5,如果斜率k(4,5)<k(3,4),4点被抛弃:不等式(yj-yk)/(xj-xk) <= sum[i],由于sum i递增,此时小于等于,即删去的点对i不会最优,对后面的i+更不会...
ε, i入队尾,由于删去γ中不满足的点后,加入后满足图像斜率依旧上升。
三:为什么i的最优值在队首取得?
ζ, 见一,删去前劣后优的点后,剩下的就是前由后劣,队首为最优点。
四:注意整理中要考虑下正负,涉及到不等号的方向,当然此题毋须多虑。
θ, 把除法转化成乘法;注意符号。
(写法是左开右闭)
#include<cstdio>
#include<cstdlib>
#include<iostream>
#include<algorithm>
#include<cstring>
using namespace std;
const int maxn=;
int dp[maxn],sum[maxn],q[maxn];
int n,m;
int getdp(int i,int j)
{
return dp[j]+(sum[i]-sum[j])*(sum[i]-sum[j])+m;
}
int getdy(int i,int j)
{
return dp[i]+sum[i]*sum[i]-dp[j]-sum[j]*sum[j];
}
int getdx(int i,int j)
{
return *(sum[i]-sum[j]);
}
int main()
{
int i,j,n,head,tail;
while(~scanf("%d%d",&n,&m))
{
for(i=;i<=n;i++) scanf("%d",&sum[i]);
for(i=;i<=n;i++) sum[i]+=sum[i-];
head=tail=;q[]=;
for(i=;i<=n;i++){
while(head<tail&&(getdy(q[head+],q[head])<=sum[i]*getdx(q[head+],q[head]))) head++;
dp[i]=getdp(i,q[head]);
while(head<tail&&(getdy(i,q[tail])*getdx(i,q[tail-])<=(getdy(i,q[tail-])*getdx(i,q[tail])))) tail--;
q[++tail]=i;
}
printf("%d\n",dp[n]);
}
return ;
}
HDU3507Print Article (斜率优化DP)的更多相关文章
- hdu3507Print Article(斜率优化dp)
Print Article Time Limit: 9000/3000 MS (Java/Others) Memory Limit: 131072/65536 K (Java/Others)To ...
- HDU-3507Print Article 斜率优化DP
学习:https://blog.csdn.net/bill_yang_2016/article/details/54667902 HDU-3507 题意:有若干个单词,每个单词有一个费用,连续的单词组 ...
- HDU3507 Print Article(斜率优化dp)
前几天做多校,知道了这世界上存在dp的优化这样的说法,了解了四边形优化dp,所以今天顺带做一道典型的斜率优化,在百度打斜率优化dp,首先弹出来的就是下面这个网址:http://www.cnblogs. ...
- hdu 3507 Print Article(斜率优化DP)
题目链接:hdu 3507 Print Article 题意: 每个字有一个值,现在让你分成k段打印,每段打印需要消耗的值用那个公式计算,现在让你求最小值 题解: 设dp[i]表示前i个字符需要消耗的 ...
- hdu3507 Print Article[斜率优化dp入门题]
Print Article Time Limit: 9000/3000 MS (Java/Others) Memory Limit: 131072/65536 K (Java/Others)To ...
- HDU3507 Print Article —— 斜率优化DP
题目链接:https://vjudge.net/problem/HDU-3507 Print Article Time Limit: 9000/3000 MS (Java/Others) Mem ...
- [hdu3507 Print Article]斜率优化dp入门
题意:需要打印n个正整数,1个数要么单独打印要么和前面一个数一起打印,1次打印1组数的代价为这组数的和的平方加上常数M.求最小代价. 思路:如果令dp[i]为打印前i个数的最小代价,那么有 dp[i] ...
- Print Article /// 斜率优化DP oj26302
题目大意: 经典题 数学分析 G(a,b)<sum[i]时 a优于b G(a,b)<G(b,c)<sum[i]时 b必不为最优 #include <bits/stdc++.h& ...
- HDU3507 Print Article (斜率优化DP基础复习)
pid=3507">传送门 大意:打印一篇文章,连续打印一堆字的花费是这一堆的和的平方加上一个常数M. 首先我们写出状态转移方程 :f[i]=f[j]+(sum[i]−sum[j])2 ...
- hdu 3507 Print Article —— 斜率优化DP
题目:http://acm.hdu.edu.cn/showproblem.php?pid=3507 设 f[i],则 f[i] = f[j] + (s[i]-s[j])*(s[i]-s[j]) + m ...
随机推荐
- dojo 官方翻译 dojo/aspect
官网地址:http://dojotoolkit.org/reference-guide/1.10/dojo/aspect.html after() 定义:after(target, methodNam ...
- case的嵌套使用
case分支语句的格式如下: case $变量名 in 模式1) 命令序列1 ;; 模式2) 命令序列2 ;; *) 默认执行的命令序列 ;; esac case语句结构特点如下: 1. ...
- SVN使用—常用命令及避免冲突的方法
一.SVN启动 [root@localhost ~]# mkdir /data/svn [root@localhost ~]# svnadmin create /data/svn/test [root ...
- 高亮显示QSS文件
转[作者:一去丶二三里 博客地址:http://blog.csdn.net/liang19890820] 简述 语法高亮是文本编辑器用来显示文本的,特别是源代码,根据不同的类别来用不同的颜色和字体显示 ...
- Linux Shell脚本简介
Shell 诞生于 Unix,是与 Unix/Linux 交互的工具,单独地学习 Shell 是没有意义的,请先参考Unix/Linux入门教程,了解 Unix/Lunix 基础. 近几年来,Shel ...
- Spring容器创建过程
Spring容器的refresh() 创建刷新 1 prepareRefresh() 刷新前的预处理 1) initProPertySources() 初始化一些属性设置: 子类定义个性化的属性 ...
- jQuery的序列化元素 serialize()方法 serializeArray()方法 param()方法
当提交的表单元素较多时用serialize()方法,serialize()方法也是作用于一个jQuery的对象,它能够将DOM元素内容序列化为字符串,用于Ajax请求. serialize() 方法通 ...
- Java基本数据类型与相应的封装类
基本数据类型 封装类 int Integer short Short float Float double Double long Long boolean Boolean b ...
- scala学习手记5 - 元组与多重赋值
假定要在一个方法中返回多个值.比如需要返回一个人的名.姓和邮箱地址.在Java中最常用的方法是定义一个Person类,其中包括相对应的字段:还有些不常用的方法就是返回一个集合或数组,拿到结果后再进行循 ...
- Cacti的基本安装配置
////////////////////cacti///////////////////////////常用的监控软件有:cacti.nagios.zabbix等 cacti 重图形.有数据历史.需要 ...