传送门

斜率优化dp好题。

对于第i只猫,显然如果管理员想从出发开始刚好接到它,需要在t[i]=h[i]−dist(1,i)" role="presentation" style="position: relative;">t[i]=h[i]−dist(1,i)t[i]=h[i]−dist(1,i)的时候出发才行。

这样的话,如果把第l~r只猫分成一组,那么当前分组需要的最小花费是

t[r]−t[l]+t[r]−t[l+1]+t[r]−t[l+2]+...+t[r]−t[r]=t[r]∗(r−l+1)−(sum[r]−sum[l−1])" role="presentation" style="position: relative;">t[r]−t[l]+t[r]−t[l+1]+t[r]−t[l+2]+...+t[r]−t[r]=t[r]∗(r−l+1)−(sum[r]−sum[l−1])t[r]−t[l]+t[r]−t[l+1]+t[r]−t[l+2]+...+t[r]−t[r]=t[r]∗(r−l+1)−(sum[r]−sum[l−1])

于是就可以推出状态转移方程了:

f[i][j]=min(f[i−1][k]+a[j]∗(j−k)+(sum[j]−sum[k]))" role="presentation" style="position: relative;">f[i][j]=min(f[i−1][k]+a[j]∗(j−k)+(sum[j]−sum[k]))f[i][j]=min(f[i−1][k]+a[j]∗(j−k)+(sum[j]−sum[k]))

对于两个不同的决策k1,k2。

如果k1转移出的结果比k2优秀,那么:

f[i−1][k1]+a[j]∗(j−k1)+(sum[j]−sum[k1])&lt;f[i−1][k2]+a[j]∗(j−k2)+(sum[j]−sum[k2])" role="presentation" style="position: relative;">f[i−1][k1]+a[j]∗(j−k1)+(sum[j]−sum[k1])<f[i−1][k2]+a[j]∗(j−k2)+(sum[j]−sum[k2])f[i−1][k1]+a[j]∗(j−k1)+(sum[j]−sum[k1])<f[i−1][k2]+a[j]∗(j−k2)+(sum[j]−sum[k2])

=>((f[i−1][k1]−sum[k1])−(f[i−1][k2]−sum[k2]))&lt;a[j]∗(k1−k2)" role="presentation" style="position: relative;">((f[i−1][k1]−sum[k1])−(f[i−1][k2]−sum[k2]))<a[j]∗(k1−k2)((f[i−1][k1]−sum[k1])−(f[i−1][k2]−sum[k2]))<a[j]∗(k1−k2)

假设t[k]=f[i−1][k]−sum[k]" role="presentation" style="position: relative;">t[k]=f[i−1][k]−sum[k]t[k]=f[i−1][k]−sum[k]

=>(t[k1]−t[k2])/(k1−k2)&lt;a[j]" role="presentation" style="position: relative;">(t[k1]−t[k2])/(k1−k2)<a[j](t[k1]−t[k2])/(k1−k2)<a[j]

果断斜率优化了。

代码:

#include<bits/stdc++.h>
#define N 100005
#define ll long long
using namespace std;
inline ll read(){
    ll ans=0,w=1;
    char ch=getchar();
    while(!isdigit(ch)){if(ch=='-')w=-1;ch=getchar();}
    while(isdigit(ch))ans=(ans<<3)+(ans<<1)+(ch^48),ch=getchar();
    return ans*w;
}
int q[N],hd,tl,n,m,p,tmp;
ll dis[N],h[N],t[N],sum[N],f[2][N],ans=1e18;
inline ll gety(int k,int i,int j){return f[k][i]+sum[i]-f[k][j]-sum[j];}
inline ll getx(int i,int j){return i-j;}
int main(){
    n=read(),m=read(),p=read();
    for(int i=2;i<=n;++i)dis[i]=dis[i-1]+read();
    for(int i=1;i<=m;++i)tmp=read(),t[i]=read()-dis[tmp];
    sort(t+1,t+m+1);
    for(int i=1;i<=m;++i)sum[i]=sum[i-1]+t[i];
    fill(f[0]+1,f[0]+m+1,1e18);
    int las=0;
    for(int i=1;i<=p;++i){
        hd=tl=1,q[1]=0,las^=1;
        for(int j=1;j<=m;++j){
            while(hd<tl&&gety(las^1,q[hd+1],q[hd])<t[j]*getx(q[hd+1],q[hd]))++hd;
            int k=q[hd];
            f[las][j]=f[las^1][k]+t[j]*(j-k)-(sum[j]-sum[k]);
            while(hd<tl&&gety(las^1,q[tl],q[tl-1])*getx(j,q[tl])>gety(las^1,j,q[tl])*getx(q[tl],q[tl-1]))--tl;
            q[++tl]=j;
        }
        ans=min(ans,f[las][m]);
    }
    cout<<ans;
    return 0;
}

2018.09.07 codeforces311B. Cats Transport(斜率优化dp)的更多相关文章

  1. 2018.09.05 任务安排(斜率优化dp)

    描述 这道题目说的是,给出了n项必须按照顺序完成的任务,每项任务有它需要占用机器的时间和价值.现在我们有一台机器可以使用,它每次可以完成一批任务,完成这批任务所需的时间为一个启动机器的时间S加上所有任 ...

  2. CodeForces 311 B Cats Transport 斜率优化DP

    题目传送门 题意:现在有n座山峰,现在 i-1 与 i 座山峰有 di长的路,现在有m个宠物, 分别在hi座山峰,第ti秒之后可以被带走,现在有p个人,每个人会从1号山峰走到n号山峰,速度1m/s.现 ...

  3. Codeforces 311B Cats Transport 斜率优化dp

    Cats Transport 出发时间居然能是负的,我服了... 卡了我十几次, 我一直以为斜率优化写搓了. 我们能得出dp方程式 dp[ i ][ j ] = min(dp[ k ][ j - 1 ...

  4. CF311B Cats Transport 斜率优化DP

    题面:CF311B Cats Transport 题解: 首先我们观察到山与距离其实是没有什么用的,因为对于任意一只猫,我们都可以直接算出如果有一个人要恰好接走它,需要在哪一时刻出发,我们设第i只猫对 ...

  5. CF331B Cats Transport[斜率优化dp+贪心]

    luogu翻译 一些山距离起点有距离且不同,m只猫要到不同的山上去玩ti时间,有p个铲屎官人要去把所有猫接走,步行速度为1单位每秒,从1走到N座山不停下,必须在猫玩完后才可以把他带走.可以提前出发.问 ...

  6. 2018.09.29 bzoj3156: 防御准备(斜率优化dp)

    传送门 斜率dp经典题目. 然而算斜率的时候并没有注意到下标的平方会爆int于是咕咕*2. 这道题我用了两个数组来表示状态. f[i]f[i]f[i]表示最后i个位置倒数第i个放木偶的最优值. g[i ...

  7. 【题解】Cats Transport (斜率优化+单调队列)

    [题解]Cats Transport (斜率优化+单调队列) # When Who Problem Lang Verdict Time Memory 55331572 Jun/09/2019 19:1 ...

  8. $CF311B\ Cats\ Transport$ 斜率优化

    AcWing Description Sol 设f[i][j]表示前i个饲养员接走前j只猫咪的最小等待时间. 要接到j猫咪,饲养员的最早出发时间是可求的,设为d: $ d[j]=Tj-\sum_{k= ...

  9. 2018.09.07 Amount of degrees(数位dp)

    描述 求给定区间[X,Y]中满足下列条件的整数个数:这个数恰好等于K个互不相等的B的整数次幂之和. 例如,设X=15,Y=20,K=2,B=2,则有且仅有下列三个数满足题意: 17 = 24+20, ...

随机推荐

  1. java中正则表达式,编译报错:Invalid escape sequence (valid ones are \b \t \n \f \r \" \' \\ )

    转自:https://www.cnblogs.com/EasonJim/p/6561666.html 若出现:Invalid escape sequence (valid ones are  \b   ...

  2. angular ng-bind-html

    使用ng-bind-html 可以在页面上展示html内容,让html内容加进去后不是一代码形式出现,而是以页面形式展现 需要先引入angular-sanitize.min.js,这个可以在githu ...

  3. Activity服务类-5 IdentityService服务类

    一.内置用户组(角色)设计表概念 用户和组(或者叫做角色),多对多关联,通过关联表实现 act_id_user 用户表: act_id_group 用户组表: act_id_membership 用户 ...

  4. Objective C, erum 枚举类型

    typedef NS_ENUM(NSInteger, MYENUM) { TYPE1, TYPE2, TYPE3 };

  5. rem 的使用

    1.填加以下代码 (function (designWidth, maxWidth) { var doc = document, win = window, docEl = doc.documentE ...

  6. 使用JavaScript的XMLHttpRequest发送POST、GET请求以及接收返回值

    使用XMLHttpRequest对象分为4部完成: 1.创建XMLHttpRequest组建 2.设置回调函数 3.初始化XMLHttpRequest组建 4.发送请求 实例代码: [javascri ...

  7. Ubuntu 安装 Elasticsearch

    1.安装java 注意:最新版本的elasticsearch(5.6.2)要求安装java8 1.sudo apt-add-repository ppa:webupd8team/java 2.sudo ...

  8. git cherry-pick用法

    场景: 如果你的应用已经发布了一个版本2.0, 代码分支叫release-2.0, 现在正在开发3.0, 代码的分支叫dev-3.0. 那么有一天产品说, 要把正在开发的某个特性提前上线, 也就是说要 ...

  9. Nexus 按项目类型分配不同的工厂来发布不同 项目

    但是有时候,一个公司会有很多项目[crm,oa,erp]等等的项目.如果把这些项目全部都放到releases或者snapshots中的话会有点混乱.比较好的办法是,按项目来分.每个项目一个工厂:cms ...

  10. referer null

    Referer表示超链接源的URL!你想看到实验效果,要从a-->(能过<a href="b.jsp")b页面,然后在B里可以取得Refere参数! String ur ...