HNOI 2008 玩具裝箱TOY 斜率優化dp

2021-07-30 01:40:30 字數 2050 閱讀 7398

description

p教授要去看奧運,但是他捨不下他的玩具,於是他決定把所有的玩具運到北京。他使用自己的壓縮器進行壓

縮,其可以將任意物品變成一堆,再放到一種特殊的一維容器中。p教授有編號為1…n的n件玩具,第i件玩具經過

壓縮後變成一維長度為ci.為了方便整理,p教授要求在乙個一維容器中的玩具編號是連續的。同時如果乙個一維容

器中有多個玩具,那麼兩件玩具之間要加入乙個單位長度的填充物,形式地說如果將第i件玩具到第j個玩具放到一

個容器中,那麼容器的長度將為 x=j-i+sigma(ck) i<=k<=j 製作容器的費用與容器的長度有關,根據教授研究,

如果容器長度為x,其製作費用為(x-l)^2.其中l是乙個常量。p教授不關心容器的數目,他可以製作出任意長度的容

器,甚至超過l。但他希望費用最小.

input

第一行輸入兩個整數n,l.接下來n行輸入ci.1<=n<=50000,1<=l,ci<=10^7

output

輸出最小費用

思路: 設s

um[i

] 表示

c 的字首和,則很容易得到o(

n2)的轉移方程: dp

[i]=

min

為了簡化方程,設g[

i]=s

um[i

]+i,

c=l+

1 , 於是轉移方程為: dp

[i]=

min

考慮兩種決策

j<

k ,則k比j優,當且僅當: dp

[j]+

(g[i

]−g[

j]−c

)2>dp

[k]+

(g[i

]−g[

k]−c

)2 g

[i]>dp

[k]−

dp[j

]+(g

[k]−

c)2+

(g[j

]−c)

22(g

[k]−

g[j]

) 我們記 sl

ope(

j,k)

=dp[

k]−d

p[j]

+(g[

k]−c

)2+(

g[j]

−c)2

2(g[

k]−g

[j])

為j到k的斜率,作為判斷哪個決策更優的依據. 由於g

[i] 單增,如果當前k比j優,則之後也必有k比j優,即轉移具有決策單調性.那我們就可以維護乙個單調佇列,其中記錄了一些決策點,且相鄰元素的的斜率單增.更新dp

[i] 時,只需判斷隊首的兩個元素的斜率是否有s≥

g[i]

,若是則說明第二個元素作為決策點更優,彈掉隊首.然後直接取隊首作為決策點更新dp

[i] ,並將i作為決策點插入隊尾,但要保持佇列中的斜率單調性.

source:

#include 

#include

#include

#include

#define for(i, j, k) for(int i = j; i <= k; i++)

#define forr(i, j, k) for(int i = j; i >= k; i--)

const int n = 50010;

typedef long long ll;

ll sum[n], g[n], dp[n], c;

int n, que[n];

inline ll s

qr(ll x)

inline ll cx(int l, int r)

inline ll cy(int l, int r)

int main()

int fst = 1, lst = 1;

que[1] = 0;

for(i, 1, n)

printf("%lld\n", dp[n]);

return

0;}

HNOI2008 玩具裝箱toy

重點在講斜率優化 description p教授要去看奧運,但是他捨不下他的玩具,於是他決定把所有的玩具運到北京。他使用自己的壓縮器進行壓縮,其可以將任意物品變成一堆,再放到一種特殊的一維容器中。p教授有編號為1.n的n件玩具,第i件玩具經過壓縮後變成一維長度為ci.為了方便整理,p教授要求在乙個一...

HNOI2008 玩具裝箱toy

dp i min dp j sum i sum j c 2 dp k sum i sum k c 2 dp k si sum k 2 dp k si 2 2 si sum k sum k 2 dp k sum k 2 dp j sum j 2 2 si sum k sum j yk yj 2 si ...

HNOI2008 玩具裝箱TOY

題目描述 p教授要去看奧運,但是他捨不下他的玩具,於是他決定把所有的玩具運到北京。他使用自己的壓縮器進行壓縮,其可以將任意物品變成一堆,再放到一種特殊的一維容器中。p教授有編號為1 n的n件玩具,第i件玩具經過壓縮後變成一維長度為ci.為了方便整理,p教授要求在乙個一維容器中的玩具編號是連續的。同時...