HNOI2008玩具装箱toy题解

  • 题目描述 Description

    P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京。他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中。P教授有编号为1...N的N件玩具,第i件玩具经过压缩后变成一维长度为Ci.为了方便整理,P教授要求在一个一维容器中的玩具编号是连续的。同时如果一个一维容器中有多个玩具,那么两件玩具之间要加入一个单位长度的填充物,形式地说如果将第i件玩具到第j个玩具放到一个容器中,那么容器的长度将为x=j?i+Sigmajk=i(Ck) 制作容器的费用与容器的长度有关,根据教授研究,如果容器长度为x,其制作费用为(x?L)2.其中L是一个常量。P教授不关心容器的数目,他可以制作出任意长度的容器,甚至超过L。但他希望费用最小.

  • 输入描述 Input Description

    第一行输入两个整数N,L.接下来N行输入Ci,1≤N≤50000,1≤L,Ci≤107

  • 输出描述 Output Description

    输出最小费用

  • 样例输入 Sample Input

    5 4

    3

    4

    2

    1

    4

  • 样例输出 Sample Output

    1

  • 题解

    首先推荐一篇文章《1D1D动态规划优化初步》,上面详细地介绍了单调栈优化的方法。

    令f[i]表示前i件玩具放入容器内的最小代价,通过一些简单的分析,我们可以得到这样一个DP方程:

    f[i]=mini?1j=0{f[j]+w(j+1,i)},(f[0]=0),

    其中w(x,y)=(y?x+Sigmayi=x(Ci)?L)2,

    我们把C数组处理成前缀和,那么w(x,y)可在O(1)的时间内算出,直接求解的话整个方程的时间复杂度是O(n2)。

    设当f[i]取到最优值时f[i]=f[k]+w(k+1,i),则记f[i]由决策k转移过来。//那么i=1时应有k=0。

    可以证明(也可以打出决策表来观察)这个方程中k的值是单调不降的。所以可以套用单调栈优化,时间复杂度O(nlog2n)通过本题。

    注意开longlong,不要unsigned。

  • Code
#include <cstdio>
#include <cstring>
#include <algorithm>
#define ll long long
using namespace std;
const int maxn = 50010;
ll f[maxn], c[maxn];
int n, L, top;
struct stack          //决策栈
{
    int k, s, t;
    stack(int k = 0, int s = 0, int t = 0) :k(k), s(s), t(t) {}
} S[maxn];
void init()
{
    scanf("%d%d", &n, &L);
    for(int i = 1; i <= n; ++i)
    {
        scanf("%lld", &c[i]);
        c[i] += c[i - 1];
    }
}
inline ll w(int x, int y)
{
    return (y - x + c[y] - c[x - 1] - L) * (y - x + c[y] - c[x - 1] - L);
}
void work()
{
    f[0] = 0;
    S[++top] = stack(0, 0, n);
    for(int i = 1; i <= n; ++i)
    {
        int lft = 1, rit = top, mid;
        while(lft <= rit)            //计算f[i]
        {
            mid = ((lft + rit) >> 1);
            if(S[mid].s <= i && S[mid].t >= i)
            {
                f[i] = f[S[mid].k] + w(S[mid].k + 1, i);
                break;
            }
            if(i < S[mid].s) rit = mid - 1;
            else lft = mid + 1;
        }
        while(top > 0)              //更新决策栈
        {
            if(f[S[top].k] + w(S[top].k + 1, S[top].s) < f[i] + w(i + 1, S[top].s))
            {
                lft = S[top].s; rit = S[top].t;
                while(lft <= rit)
                {
                    mid = ((lft + rit) >> 1);
                    if(f[S[top].k] + w(S[top].k + 1, mid) < f[i] + w(i + 1, mid)) lft = mid + 1;
                    else rit = mid - 1;
                }
                S[top].t = rit;
                break;
            }
            --top;
        }
        if(lft <= n) S[++top] = stack(i, lft, n);
    }
    printf("%lld", f[n]);
}
int main()
{
    init();
    work();
    return 0;
}

版权声明:本文为博主原创文章,未经博主允许不得转载。

时间: 2024-10-14 04:52:42

HNOI2008玩具装箱toy题解的相关文章

斜率优化专题2——bzoj 1010 [HNOI2008]玩具装箱toy 题解

[原题] 1010: [HNOI2008]玩具装箱toy Time Limit: 1 Sec  Memory Limit: 162 MB Submit: 5434  Solved: 1969 [Submit][Status] Description P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为1...N的N件玩具,第i件玩具经过压缩后变成一维长度为Ci.为了方便整理,P教授

BZOJ 1010 [HNOI2008]玩具装箱toy

1010: [HNOI2008]玩具装箱toy Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 7184  Solved: 2724[Submit][Status][Discuss] Description P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为1...N的N件玩具,第i件玩具经过压缩后变成一维长度为Ci.为了方便整理,P

BZOJ 1010: [HNOI2008]玩具装箱toy 斜率优化DP

1010: [HNOI2008]玩具装箱toy Description P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为1...N的N件玩具,第i件玩具经过压缩后变成一维长度为Ci.为了方便整理,P教授要求在一个一维容器中的玩具编号是连续的.同时如果一个一维容器中有多个玩具,那么两件玩具之间要加入一个单位长度的填充物,形式地说如果将第i件玩具到第j个玩具放到一个容器中,那么容器

BZOJ 1010: [HNOI2008]玩具装箱toy [DP 斜率优化]

1010: [HNOI2008]玩具装箱toy Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 9812  Solved: 3978[Submit][Status][Discuss] Description P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为1...N的N件玩具,第i件玩具经过压缩后变成一维长度为Ci.为了方便整理,P

BZOJ 1010: [HNOI2008]玩具装箱toy(DP+斜率优化)

[HNOI2008]玩具装箱toy Description P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为1...N的N件玩具,第i件玩具经过压缩后变成一维长度为Ci.为了方便整理,P教授要求在一个一维容器中的玩具编号是连续的.同时如果一个一维容器中有多个玩具,那么两件玩具之间要加入一个单位长度的填充物,形式地说如果将第i件玩具到第j个玩具放到一个容器中,那么容器的长度将为

bzoj 1010 [HNOI2008]玩具装箱toy(DP的斜率优化)

1010: [HNOI2008]玩具装箱toy Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 7874  Solved: 3047[Submit][Status][Discuss] Description P 教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维 容器中.P教授有编号为1...N的N件玩具,第i件玩具经过压缩后变成一维长度为Ci.为了方便整理

HNOI2008 玩具装箱toy (BZOJ1010,斜率dp)

传送门 1010: [HNOI2008]玩具装箱toy Time Limit: 1 Sec  Memory Limit: 162 MB Description P 教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维 容器中.P教授有编号为1...N的N件玩具,第i件玩具经过压缩后变成一维长度为Ci.为了方便整理,P教授要求在一个一维容器中的玩具编号是连续的. 同时如果一个一维容器中有多个玩具,那么两件玩

bzoj 1010: [HNOI2008]玩具装箱toy 2011-12-27

1010: [HNOI2008]玩具装箱toy Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 2254  Solved: 744[Submit][Status][Discuss] DescriptionP 教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维 容器中.P教授有编号为1...N的N件玩具,第i件玩具经过压缩后变成一维长度为Ci.为了方便整理,P

1010: [HNOI2008]玩具装箱toy(斜率优化)

1010: [HNOI2008]玩具装箱toy Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 12280  Solved: 5277[Submit][Status][Discuss] Description P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为1...N的N件玩具,第i件玩具经过压缩后变成一维长度为Ci.为了方便整理,