• BZOJ4268 : 小强的书架


    首先将所有高度乘上10,设f[i]为将前i本书放入书架的最小高度,则

    [egin{eqnarray*}
    f[i]&=&min(f[j-1]+first(j,i)+second(j,i)+W-(s[i]-s[j-1]))\
    &=&min(f[j-1]+first(j,i)+second(j,i)+W-s[i]+s[j-1])\
    &=&min(f[j-1]+first(j,i)+second(j,i)+s[j-1])+W-s[i]
    end{eqnarray*}]

    其中$1leq jleq i$且$s[i]-s[j-1]leq W$。

    设tmp[i][j]=f[j-1]+s[j-1]+first(j,i)+second(j,i),考虑用线段树维护tmp[i][j],如果当前要计算f[i],那么线段树的第j个叶子节点就表示tmp[i][j]。

    为了高效维护first和second,先将所有书按高度排序,从大到小插入到set中。

    假设现在插入的是第x本书,那么对于[pre(x)+1,x]内的i,first(i,x)均为a[x]。

    对于[pre(pre(x))+1,pre(x)]内的i,以及[x,nxt(x)-1]内的j,second(i,j)均为a[x]。

    对于[pre(x)+1,x]内的i,以及[nxt(x),nxt(nxt(x))-1]内的j,second(i,j)也均为a[x]。

    于是在右端点的最小值处进行区间赋值操作即可。


    时间复杂度$O(nlog n)$。

    #include<cstdio>
    #include<algorithm>
    #include<set>
    #define N 300010
    using namespace std;
    typedef long long ll;
    int n,w,i,j,k,c[N],l[N],g[N],vl[N<<1],vr[N<<1],nxt[N<<1],ed;ll a[N],b[N],vw[N<<1],f;
    set<int>T;set<int>::iterator it;
    inline bool cmp(int x,int y){return a[x]<a[y];}
    inline int get(){char c;while(!(((c=getchar())>='0')&&(c<='9')));int a=c-'0';while(((c=getchar())>='0')&&(c<='9'))(a*=10)+=c-'0';return a;}
    inline void add(int x,int l,int r,ll w){vl[++ed]=l;vr[ed]=r;vw[ed]=w;nxt[ed]=g[x];g[x]=ed;}
    struct node{ll v1,v2,vc,v,t1,t2;}S[1050000];
    inline void tag1(int x,ll p){
      S[x].v1=p+S[x].vc;
      S[x].v=p+S[x].v2;
      S[x].t1=p;
    }
    inline void tag2(int x,ll p){
      S[x].v2=p+S[x].vc;
      S[x].v=p+S[x].v1;
      S[x].t2=p;
    }
    inline void pb(int x){
      if(S[x].t1){
        tag1(x<<1,S[x].t1);
        tag1(x<<1|1,S[x].t1);
        S[x].t1=0;
      }
      if(S[x].t2){
        tag2(x<<1,S[x].t2);
        tag2(x<<1|1,S[x].t2);
        S[x].t2=0;
      }
    }
    inline void up(int x){
      S[x].v1=min(S[x<<1].v1,S[x<<1|1].v1);
      S[x].v2=min(S[x<<1].v2,S[x<<1|1].v2);
      S[x].vc=min(S[x<<1].vc,S[x<<1|1].vc);
      S[x].v=min(S[x<<1].v,S[x<<1|1].v);
    }
    void same1(int x,int a,int b,int c,int d,ll p){
      if(c<=a&&b<=d){tag1(x,p);return;}
      pb(x);
      int mid=(a+b)>>1;
      if(c<=mid)same1(x<<1,a,mid,c,d,p);
      if(d>mid)same1(x<<1|1,mid+1,b,c,d,p);
      up(x);
    }
    void same2(int x,int a,int b,int c,int d,ll p){
      if(c<=a&&b<=d){tag2(x,p);return;}
      pb(x);
      int mid=(a+b)>>1;
      if(c<=mid)same2(x<<1,a,mid,c,d,p);
      if(d>mid)same2(x<<1|1,mid+1,b,c,d,p);
      up(x);
    }
    void change(int x,int a,int b,int c,ll p){
      if(a==b){
        S[x].vc=p;
        S[x].v1=p+S[x].t1;
        S[x].v2=p+S[x].t2;
        S[x].v=p+S[x].t1+S[x].t2;
        return;
      }
      pb(x);
      int mid=(a+b)>>1;
      c<=mid?change(x<<1,a,mid,c,p):change(x<<1|1,mid+1,b,c,p);
      up(x);
    }
    ll ask(int x,int a,int b,int c,int d){
      if(c<=a&&b<=d)return S[x].v;
      pb(x);
      int mid=(a+b)>>1;ll t=1LL<<60;
      if(c<=mid)t=ask(x<<1,a,mid,c,d);
      if(d>mid)t=min(t,ask(x<<1|1,mid+1,b,c,d));
      return up(x),t;
    }
    int main(){
      n=get(),w=get();
      for(i=1;i<=n;i++)a[i]=10LL*get(),b[i]=b[i-1]+get(),c[i]=i;
      for(sort(c+1,c+n+1,cmp),T.insert(0),T.insert(n+1),i=n;i;i--){
        T.insert(c[i]);
        it=T.find(c[i]);
        it--,j=*it,l[c[i]]=*it+1;
        if(j)it--,add(c[i],*it+1,j,a[c[i]]);
        it=T.find(c[i]);
        it++,j=*it;
        if(j<=n)add(j,l[c[i]],c[i],a[c[i]]);
      }
      for(i=j=1;i<=n;i++){
        same1(1,1,n,l[i],i,a[i]);
        same2(1,1,n,i,i,a[i]);
        for(k=g[i];k;k=nxt[k])same2(1,1,n,vl[k],vr[k],vw[k]);
        while(b[i]-b[j-1]>w)j++;
        f=ask(1,1,n,j,i)+w-b[i];
        if(i<n)change(1,1,n,i+1,f+b[i]);
      }
      return printf("%lld.%d",f/10,f%10),0;
    }
    

      

  • 相关阅读:
    <WP7>(三)手把手教你写天气预报程序:运用WebClient获取天气和json数据解析
    <WP7>(二)手把手教你写天气预报程序:UserControl的运用
    <cocos2dx for wp7>使用cocos2dx和BOX2D来制作一个BreakOut(打砖块)游戏(一)
    <WP7>(一)手把手教你写天气预报程序:序言
    <cocos2dx for wp7>使用cocos2dx和BOX2D来制作一个BreakOut(打砖块)游戏(二)
    <cocos2dx for wp7>使用box2d来做碰撞检测(且仅用来做碰撞检测)
    JQuery的开发与使用心得
    babylonjs
    [算法简结]动态规划(一):承
    centos7相关操作
  • 原文地址:https://www.cnblogs.com/clrs97/p/4830767.html
Copyright © 2020-2023  润新知