1 条题解

  • 1
    @ 2022-8-5 20:19:52

    首先每个球的初始高度不影响决策,真正有影响的在于其 vv 值。

    按横坐标排序,进行区间 dp。

    fl,r,opf_{l,r,op} 表示考虑 lrl\sim r 的球,当前在左 / 右端点时对于答案已有的最小损失。特别的,我们把起点变为一个 v=0v=0 的球。

    损失包括内部的损失以及外部的损失

    这就是一种贡献提前计算的思想。

    于是有 dp 方程(可能有些长):

    $$f_{l,r,0}=\min\{f_{l+1,r,0}+(x_{l+1}-x_l)\times((\sum v)-(\sum_{i=l+1}^rv)),f_{l+1,r,1}+(x_r-x_l)\times((\sum v)-(\sum_{i=l+1}^rv))\} $$$$f_{l,r,1}=\min\{f_{l,r-1,1}+(x_r-x_{r-1})\times((\sum v)-(\sum_{i=l}^{r-1}v)),f_{l,r-1,0}+(x_r-x_l)\times((\sum v)-(\sum_{i=l}^{r-1}v))\} $$

    最后答案即 f0,n+y1000-f_{0,n}+\sum y\over1000

    直接 dp 即可。

    复杂度 O(n2)O(n^2)

    #include <algorithm>
    #include <stdio.h>
    #include <vector>
    typedef long long llt;
    typedef unsigned uint;typedef unsigned long long ullt;
    typedef bool bol;typedef char chr;typedef void voi;
    typedef double dbl;
    template<typename T>bol _max(T&a,T b){return(a<b)?a=b,true:false;}
    template<typename T>bol _min(T&a,T b){return(b<a)?a=b,true:false;}
    template<typename T>T lowbit(T n){return n&-n;}
    template<typename T>T gcd(T a,T b){return b?gcd(b,a%b):a;}
    template<typename T>T lcm(T a,T b){return(a!=0||b!=0)?a/gcd(a,b)*b:(T)0;}
    template<typename T>T exgcd(T a,T b,T&x,T&y){if(b!=0){T ans=exgcd(b,a%b,y,x);y-=a/b*x;return ans;}else return y=0,x=1,a;}
    template<typename T>T power(T base,T index,T mod)
    {
        T ans=1%mod;
        while(index)
        {
            if(index&1)ans=ans*base%mod;
            base=base*base%mod,index>>=1;
        }
        return ans;
    }
    llt Dp[2][1005][1005];
    struct point{llt x,v;uint id;}P[10005];
    llt VSum[1005][1005];
    int main()
    {
    #ifdef MYEE
        freopen("QAQ.in","r",stdin);
        // freopen("QAQ.out","w",stdout);
    #endif
        uint n;scanf("%u%lld",&n,&P[0].x);llt ans=0,g=0,w;
        for(uint i=1;i<=n;i++)scanf("%lld",&P[i].x),P[i].id=i;
        for(uint i=1;i<=n;i++)scanf("%lld",&w),ans+=w;
        for(uint i=1;i<=n;i++)scanf("%lld",&P[i].v),g+=P[i].v;
        std::sort(P,P+n+1,[](point a,point b){return a.x<b.x;});
        for(uint i=0;i<=n;i++)VSum[i][i]=P[i].v,Dp[0][i][i]=Dp[1][i][i]=P[i].id?1e12:0;
        for(uint d=1;d<=n;d++)for(uint l=0;l+d<=n;l++)
            VSum[l][l+d]=VSum[l][l+d-1]+P[l+d].v,
            Dp[0][l][l+d]=std::min(Dp[0][l+1][l+d]+(P[l+1].x-P[l].x)*(g-VSum[l+1][l+d]),
                Dp[1][l+1][l+d]+(P[l+d].x-P[l].x)*(g-VSum[l+1][l+d])),
            Dp[1][l][l+d]=std::min(Dp[1][l][l+d-1]+(P[l+d].x-P[l+d-1].x)*(g-VSum[l][l+d-1]),
                Dp[0][l][l+d-1]+(P[l+d].x-P[l].x)*(g-VSum[l][l+d-1]));
        ans-=std::min(Dp[0][0][n],Dp[1][0][n]);
        printf("%.3lf\n",ans/1000.);
        return 0;
    }
    
    • 1

    信息

    ID
    2037
    时间
    1000ms
    内存
    64MiB
    难度
    10
    标签
    (无)
    递交数
    8
    已通过
    5
    上传者