BZOJ 1010 [HNOI2008]玩具裝箱toy

來源:互聯網
上載者:User

標籤:

1010: [HNOI2008]玩具裝箱toyTime Limit: 1 Sec  Memory Limit: 162 MB
Submit: 7184  Solved: 2724
[Submit][Status][Discuss]
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

輸出最小費用

Sample Input5 4
3
4
2
1
4
Sample Output1HINT Source

題解:laishao_yuan:Dp先入腦

有一個Dp[i]:=min(Dp[j]+(sum[i]-sum[j]+i-j-1-L)^2)的基本思路預先處理可以得到F[i]:=sum[i]+i;令C=L+1可以簡化方程:Dp[i]:=min(Dp[j]+(F[i]-F[j]-c)^2))明顯這個為O(N^2)的演算法,,要再簡化;一維的Dp可以想到斜率最佳化 所謂斜率最佳化,個人的感悟就是:當 I:1-->n J:1-->n的N^2迴圈時 可以簡化J的迴圈 把1~N依次入隊出隊,當i要選擇j時,先根據最優策略縮短隊列,再在選取隊首元素直接作為J,算出Dp[i];這樣做的話每個數進出一次隊列 複雜度就變為O(n); 但是這樣做必須證明單調性,也就是出隊的元素在以後的Dp中不會再被利用 下面說說怎麼縮短隊列Dp[i]:=min(Dp[j]+(F[i]-F[j]-c)^2))中j的選擇是決定Dp[i]的大小的 而 f[i]、c這樣的常量是不變的(對於同一個i來說)所以我們把不含j的變數分離出來,方便運算Dp[i]:=min(Dp[j]+F[j]^2-2F[i]F[j]+2F[j]*c)+F[i]^2+c^2-2*F[i]*c;假設選j好過選k, 本題為Dp[j]+F[j]^2-2F[i]F[j]+2F[j]*c<Dp[k]+F[k]^2-2F[i]F[k]+2F[k]*c化簡分離i Dp[j]-Dp[k]+(F[i]-F[k])*(2c+F[j]+F[k])-------------------------------------------<F[i](*)                   2(F[j]-F[k]) 簡化其為COM(j,k)<F[i]也就是說 ‘選j好過選k’若且唯若‘COM(j,k)<F[i]成立’所以如果一個隊列的頭依次為A,B 如果G(B,A)<=F[i] 那麼把A刪了吧代碼們:
 1 #include<iostream> 2 #include<cstdio> 3 #include<cmath> 4 #include<algorithm> 5 #include<queue> 6 #include<cstring> 7 #define PAU putchar(‘ ‘) 8 #define ENT putchar(‘\n‘) 9 using namespace std;10 const int maxn=50010;typedef long long LL;11 int deq[maxn];LL C[maxn],S[maxn],dp[maxn];12 double slope(int i,int j){return (dp[i]+S[i]*S[i]-dp[j]-S[j]*S[j])/(double)(S[i]-S[j]);}13 inline int read(){14     int x=0,sig=1;char ch=getchar();15     while(!isdigit(ch)){if(ch==‘-‘)sig=-1;ch=getchar();}16     while(isdigit(ch))x=10*x+ch-‘0‘,ch=getchar();17     return x*sig;18 }19 inline LL readl(){20     LL x=0,sig=1;char ch=getchar();21     while(!isdigit(ch)){if(ch==‘-‘)sig=-1;ch=getchar();}22     while(isdigit(ch))x=10*x+ch-‘0‘,ch=getchar();23     return x*sig;24 }25 inline void write(LL x){26     if(x==0){putchar(‘0‘);return;}if(x<0)putchar(‘-‘),x=-x;27     int len=0;LL buf[15];while(x)buf[len++]=x%10,x/=10;28     for(int i=len-1;i>=0;i--)putchar(buf[i]+‘0‘);return;29 }30 int n,L;31 void init(){32     n=read();L=read();C[0]=S[0]=0;33     for(int i=1;i<=n;i++){C[i]=readl();C[i]+=C[i-1];S[i]=i+C[i];}34     return;35 }36 void work(){37     int s=0,e=0;dp[0]=deq[s]=0;38     for(int i=1;i<=n;i++){39         LL m=S[i]-L-1;40         while(s<e&&slope(deq[s+1],deq[s])<=(m<<1))++s;41         int j=deq[s];dp[i]=dp[j]+(m-S[j])*(m-S[j]);42         while(s<e&&slope(deq[e],deq[~-e])>=slope(i,deq[e]))--e;43         deq[++e]=i;44     }45     return;46 }47 void print(){48     write(dp[n]);49     return;50 }51 int main(){init();work();print();return 0;}

 

BZOJ 1010 [HNOI2008]玩具裝箱toy

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.