[Apio2014]序列分割

來源:互聯網
上載者:User

標籤:href   ret   stat   pre   status   sum   i++   esc   子序列   

3675: [Apio2014]序列分割Time Limit: 40 Sec  Memory Limit: 128 MB
[Submit][Status][Discuss]
Description小H最近迷上了一個分隔序列的遊戲。在這個遊戲裡,小H需要將一個長度為n的非負整數序列分割成k+1個非空的子序列。為了得到k+1個子序列,小H需要重複k次以下的步驟:1.小H首先選擇一個長度超過1的序列(一開始小H只有一個長度為n的序列——也就是一開始得到的整個序列);2.選擇一個位置,並通過這個位置將這個序列分割成連續的兩個非空的新序列。 每次進行上述步驟之後,小H將會得到一定的分數。這個分數為兩個新序列中元素和的乘積。小H希望選擇一種最佳的分割方式,使得k輪之後,小H的總得分最大。 Input

輸入第一行包含兩個整數n,k(k+1≤n)。

第二行包含n個非負整數a1,a2,...,an(0≤ai≤10^4),表示一開始小H得到的序列。Output

輸出第一行包含一個整數,為小H可以得到的最大分數。

Sample Input7 3
4 1 3 4 0 2 3
Sample Output108
 首先可以證明分數與切割順序無關dp[i][j]表示到第i個數,分了j組的最大分數可以通過枚舉前j-1組分到了哪兒來轉移狀態轉移方程  dp[i][j]=dp[k][j-1]+sum[k]*(sum[i]-sum[k])  sum表示首碼和第二維壓去,斜率最佳化  一定注意單調隊列的初始值因為分j組至少要有j個數,所以枚舉要從j開始而它必須由前j-1個數分為了j-1組轉移過來所以單調隊列開始有j-1 如果用斜率最佳化分母可能為0,先把0去掉 
#include<cstdio>#include<iostream>#define N 100001using namespace std;long long sum[N],now[N],last[N];int head,tail,q[N],a[N];void read(int &x){    x=0; char c=getchar();    while(!isdigit(c))  c=getchar();    while(isdigit(c)) { x=x*10+c-‘0‘; c=getchar(); }}long long up(int k,int j){    return last[j]-last[k]-sum[j]*sum[j]+sum[k]*sum[k];}long long down(int k,int j){    return sum[k]-sum[j];}int main(){    int n,k;    read(n); read(k); k++;    for(int i=1;i<=n;i++) read(a[i]);    int tot=0;    for(int i=1;i<=n;i++) if(a[i]) sum[++tot]=a[i];    for(int i=1;i<=tot;i++) sum[i]+=sum[i-1];    int j;    long long ans=0;    for(int K=2;K<=k;K++)    {        head=1; tail=1; q[1]=K-1;        for(int i=K;i<=tot;i++)        {            while(head<tail && up(q[head],q[head+1])>=down(q[head],q[head+1])*sum[i]) head++;            j=q[head];            now[i]=last[j]+sum[j]*(sum[i]-sum[j]);            while(head<tail && up(q[tail-1],q[tail])*down(q[tail],i)>=up(q[tail],i)*down(q[tail-1],q[tail])) tail--;            q[++tail]=i;        }        ans=max(ans,now[tot]);        swap(now,last);    }    printf("%lld",ans);}

 

 

[Apio2014]序列分割

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在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.