传送门

Luogu

解题思路

\(\text{DP}\) 很显然:

设 \(dp_i\) 表示前 \(i\) 个玩具的最小费用,转移就是:

\(dp_i = \max\limits_{0\le j < i}\left\{dp_j+(i-j-1+s_i-s_j-L)^2\right\}\)

\(s_i=\sum_{j=1}^ic_j\),但这是 \(O(n^2)\) 的,显然不够优秀,考虑进一步优化。

我们可以化简一下这个式子:

假设 \(dp_i\) 成功从 \(dp_j\) 转移过来,那么就有:

\(dp_i=dp_j+(i-j-1+s_i-s_j-L)^2\)

整理一下式子:

设 \(a_i = s_i+i-L-1,b_i=s_i+i\)

那么就有:

\(dp_i=dp_j+(a_i-b_j)^2\)

展开并移项可得:

\(dp_j+b_j^2=2a_ib_j+dp_i-a_i^2\)

再设 \(x_i=2b_i,y_i=dp_i+b_i^2\)

\(y_j=a_ix_j+dp_i-a_i^2\)

又因为 \(a_i^2\) 是定值,要最小化 \(dp_i\) ,那么就相当于坐标系中一条斜率为 \(a_i\) 的经过点 \((x_j, y_j)\) ,使得它的纵截距最小化。

又因为我们的 \(a_i, b_i\) 都是递增的,显然这些可能的转移点都要在下凸壳上才能使截距最小。

所以我们用单调队列,维护一下凸包上的转移点。

当前最优转移点从队头不断弹出不最优的点,并用最后的合法情况转移 \(dp_i\)。

插入当前的 \(i\) 时,为了确保凸包的性质,先不断从队尾弹出不合法的点,再插入 \(i\)。

最后输出答案 \(dp_n\)。

细节注意事项

  • 咕咕咕

参考代码

#include <algorithm>
#include <iostream>
#include <cstdio>
#define rg register
using namespace std; typedef double db;
const int _ = 50010; int n, L; db dp[_], s[_], A[_], B[_];
int hd = 1, tl = 1, Q[_]; inline db X(int i) { return (db) B[i]; } inline db Y(int i) { return (db) dp[i] + B[i] * B[i]; } inline db slope(int i, int j) { return (db) (Y(j) - Y(i)) / (X(j) - X(i)); } int main() {
#ifndef ONLINE_JUDGE
freopen("in.in", "r", stdin);
#endif
scanf("%d%d", &n, &L);
for (rg int i = 1; i <= n; ++i) scanf("%lf", s + i), s[i] += s[i - 1];
for (rg int i = 1; i <= n; ++i) A[i] = (db) s[i] + i - L - 1;
for (rg int i = 1; i <= n; ++i) B[i] = (db) s[i] + i;
for (rg int i = 1; i <= n; ++i) {
while (hd < tl && slope(Q[hd], Q[hd + 1]) < 2 * A[i]) ++hd;
dp[i] = dp[Q[hd]] + (A[i] - B[Q[hd]]) * (A[i] - B[Q[hd]]);
while (hd < tl && slope(Q[tl - 1], Q[tl]) > slope(Q[tl - 1], i)) --tl;
Q[++tl] = i;
}
printf("%lld\n", (long long) dp[n]);
return 0;
}

完结撒花 \(qwq\)

「HNOI2008」玩具装箱的更多相关文章

  1. 【BZOJ1010】【HNOI2008】玩具装箱(斜率优化,动态规划)

    [BZOJ1010][HNOI2008]玩具装箱 题面 题目描述 P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一 ...

  2. 【BZOJ】【1010】【HNOI2008】玩具装箱Toy

    DP/斜率优化 根据题目描述很容易列出动规方程:$$ f[i]=min\{ f[j]+(s[i]-s[j]+i-j-1-L)^2 \}$$ 其中 $$s[i]=\sum_{k=1}^{i} c[k] ...

  3. BZOJ_1010_[HNOI2008]_玩具装箱toy_(斜率优化动态规划+单调队列)

    描述 http://www.lydsy.com/JudgeOnline/problem.php?id=1010 给出\(n\)和\(l\).有\(n\)个玩具,第\(i\)个玩具的长度是\(c[i]\ ...

  4. 动态规划(斜率优化):BZOJ 1010 【HNOI2008】 玩具装箱

    玩具装箱toy Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 8218  Solved: 3233[Submit] Description P 教授要去 ...

  5. BZOJ 1010 【HNOI2008】 玩具装箱toy

    Description P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为1... ...

  6. 【BZOJ1010】【HNOI2008】玩具装箱

    继续看黄学长代码 原题: P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为1.. ...

  7. BZOJ 1010 [HNOI2008]toy 玩具装箱

    2017.6.9:经过我的不懈努力,终于把此题A掉了,但上凸和下凸总是那么让人费解…… P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意 ...

  8. 【HNOI2008】玩具装箱TOY & 斜率优化学习笔记

    题目 P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为 \(1\cdots N\ ...

  9. 【HNOI2008】玩具装箱

    P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为1...N的N件玩具,第i件玩具 ...

随机推荐

  1. 寒假pta二

    整除光棍 这里所谓的“光棍”,并不是指单身汪啦~ 说的是全部由1组成的数字,比如1.11.111.1111等.传说任何一个光棍都能被一个不以5结尾的奇数整除.比如,111111就可以被13整除. 现在 ...

  2. 安装树莓派实验的Pi 仪表盘

    1.简介 树莓派仪表盘网址:Pi Dashboard (Pi 仪表盘) - MAKER 趣无尽  http://maker.quwj.com/project/10 Pi Dashboard (Pi 仪 ...

  3. ESLint规则整理与实际应用

    版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明.本文链接:https://blog.csdn.net/lhb_11/article/detail ...

  4. idea代码神器:根据表生成代码

    Easycode是idea的一个插件,可以直接对数据的表生成entity,controller,service,dao,mapper,无需任何编码,简单而强大. 1.安装(EasyCode) 我这里的 ...

  5. http调用之RestTemplate

    核心方法为org.springframework.web.client.RestTemplate.doExecute(URI, HttpMethod, RequestCallback, Respons ...

  6. 【LOJ3087】「GXOI / GZOI2019」旅行者

    题意 给定一个 \(n\) 个点 \(m\) 条边的的有向图,给出 \(k\) 个关键点,求关键点两两最短路的最小值. \(n\le 10^5, m\le 5\cdot 10^5\). 题解 二进制分 ...

  7. 笔记-python-lib—data types-enum

    笔记-python-lib—data types-enum 1.      enum Source code: Lib/enum.py 文档:https://docs.python.org/3/lib ...

  8. python基础之省份三级菜单

    菜单 menu = { #定义一个字典 '北京':{ '海淀':{ '五道口':{ 'soho':{}, '网易':{}, 'google':{} }, '中关村':{ '爱奇艺':{}, '汽车之家 ...

  9. python的datetime、random和os模块使用方法

    import datetime# print(datetime.date.today())# print(datetime.datetime.today())# res=datetime.dateti ...

  10. git 从创建到推送到远程,到拉取,实操

    https://www.liaoxuefeng.com/wiki/896043488029600/900003767775424 初始化 git init 添加所有文件到暂存区 git add . c ...