UESTC_酱神赏花 2015 UESTC Training for Dynamic Programming<Problem C>

C - 酱神赏花

Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 262143/262143KB (Java/Others)

Submit Status

酱神去杭州赏花。

花展在一条街道上举行,这条街道上有一共有n个节点,自左而右从1到n编号,1号和n号是左右两个端点,两个相邻端点之间的距离为1.本次花展一共要展出m朵花,在第ti时刻,有一朵颜值为bi的花将在第ai个节点展出,如果酱神在ti时刻处于第x个节点,那么他能获得的开心值为bi−|x−ai|,注意这个值可能为负。

在t=1的时刻,酱神可以随意从1到n选出一个节点作为赏花的起点。在接下来的每个单位时间段中,酱神最多能移动d的距离。酱神每秒只能移动整数个距离,且任何时刻不能超出街道的范围。

他能获得的最大开心值为多少?

Input

第一行3个数n,m,d。

接下来m行,每行3个数ai,bi,ti。

1≤n≤105,1≤m≤100

1≤ai≤n

1≤bi≤109

1≤ti≤109

1≤d≤109

Output

输出一个数,酱神的最大开心值。

Sample input and output

Sample Input Sample Output
30 4 2
27 3 1
11 4 1
11 4 1
1 2 20
-3

解题思路:

我们令f( i , j ) -> 目前第 j 朵花开,酱神正在坐标点 i 的最小花费.

我们考虑转移

F ( i , j ) = min ( F( u , j - 1) – abs( i – u ) ) + B[j]

不妨令 i > u

F( i ,j ) = min ( F( u , j – 1 ) ) + B[j] + u – i;

当i < u时同理

这样

我们维护一个单调队列即可,正反跑两遍即可.

#include <iostream>
#include <cstring>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <cmath>

typedef long long ll;
using namespace std;
const int maxn = 1e5 + 50;
ll f[maxn][2];
int cur = 0 , q[maxn];
ll n,m,d;

typedef struct flower
{
  ll a,b,t;
  friend bool operator < (const flower & x,const flower & y)
   {
         return x.t < y.t;
   }
};

flower A[100+10];

void init_f()
{
   for(int i = 0 ; i <= n ; ++ i)
    f[i][cur] = -999999999999999;
}

int main(int argc,char *argv[])
{
  scanf("%d%d%d",&n,&m,&d);
  for(int i = 1 ; i <= m ; ++ i)
   scanf("%d%d%d",&A[i].a,&A[i].b,&A[i].t);
  sort(A+1,A+1+m);
  for(int i = 1 ; i <= n ; ++ i)
   f[i][cur] = A[1].b - abs(i - A[1].a);
  for(int j = 2 ; j <= m ; ++ j)
   {
         ll limit = (A[j].t - A[j-1].t)*d;
         cur ^= 1;
         int front = 0 , rear = 0;
         init_f();
         for(int i = 1 ; i <= n ; ++ i)
          {
             while(rear > front && f[i][cur^1] >= f[q[rear-1]][cur^1])
            rear--;
          q[rear++] = i;
          while(rear > front && (i - q[front]) > limit)
            front++;
          f[i][cur] = max(f[i][cur],f[q[front]][cur^1] + A[j].b - abs(i - A[j].a));
       }
      front = 0 , rear = 0;
      for(int i = n ; i >= 1 ; -- i)
       {
             while(rear > front && f[i][cur^1] >= f[q[rear-1]][cur^1])
              rear--;
          q[rear++] = i;
          while(rear > front && (q[front] - i) > limit)
            front++;
          f[i][cur] = max(f[i][cur],f[q[front]][cur^1] + A[j].b - abs(i - A[j].a));
       }
   }
  ll ans = -9999999999999999;
  for(int i = 1 ; i <= n ; ++ i)
   ans = max(ans,f[i][cur]);
  printf("%lld\n",ans);
  return 0;
}
时间: 2024-10-18 10:36:13

UESTC_酱神赏花 2015 UESTC Training for Dynamic Programming<Problem C>的相关文章

UESTC_酱神的旅行 2015 UESTC Training for Dynamic Programming&lt;Problem M&gt;

M - 酱神的旅行 Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submit Status 酱神要去一棵树上旅行. 酱神制定了一个旅行计划,他要按顺序去m个树上的结点,a1,a2,a3,...,am. 酱神有一辆车,树上的每一条边既可以开车通过,也可以走过去,两种方法需要不同的时间.如果选择走路,酱神需要先把车停在结点上,在他下一次要开车的时候,必须先回到停车的结点取车.

UESTC_男神的约会 2015 UESTC Training for Dynamic Programming&lt;Problem J&gt;

J - 男神的约会 Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submit Status 有一天男神约了学姐姐去看电影,电影院有一个活动,给你一个10*10的矩阵,每一个格子上都有一个0-9的整数,表示一共十种优惠券中的一种. 观众从左上角的格子开始走,走到右下角.每走到一个有着a号优惠券的格子,都必须要玩一个a分钟的游戏来领取这张优惠券. 每次只能向右或向下走.当走到右

UESTC_男神的礼物 2015 UESTC Training for Dynamic Programming&lt;Problem A&gt;

A - 男神的礼物 Time Limit: 3000/3000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submit Status Lweb学长是集训队里公认的男神.有一天他要给美美的学姐姐准备礼物. Lweb学长可是会魔法的哟.为了准备一份礼物,男神要加工n份材料.每一次只能加工相邻的材料. 当男神加工两个魔法值为a,b的材料,男神都要消耗a*b的体力,同时在这个地方合成出魔法值(a+b)%100的材料. 男神

UESTC_邱老师看电影 2015 UESTC Training for Dynamic Programming&lt;Problem F&gt;

F - 邱老师看电影 Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submit Status 一天邱老师心血来潮想去看电影,但是邱老师的妹子想去逛街,他们谁也没有办法说服对方,于是准备来玩一个游戏来决定听谁的. 邱老师找来w只白鼠和b只黑鼠,邱老师和妹子轮流从袋子里面抓老鼠,谁先抓到白色老鼠谁就赢. 但是有酱神在旁边捣乱,邱老师每抓一只老鼠出来,酱神就偷偷的也从里面抓一只出

UESTC_邱老师选妹子 2015 UESTC Training for Dynamic Programming&lt;Problem H&gt;

H - 邱老师选妹子 Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submit Status 邱老师长得帅这是人尽皆知,于是追他的妹子就会很多. 但是你知道,邱老师是一个很专一的人,所以他心里面只能有一个人. 于是他决定从追他的众多妹子里挑选一个出来.于是酱神给邱老师出来一个主意,已知有一些妹子,恰好可以给她们从l到r排号,使得每一个妹子有单独的数字,而正好有r-l+1个妹

UESTC_邱老师玩游戏 2015 UESTC Training for Dynamic Programming&lt;Problem G&gt;

G - 邱老师玩游戏 Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submit Status 邱老师最近在玩一种战略游戏,在一个地图上,有N座城堡,每座城堡都有一定的宝物,在每次游戏中邱老师允许攻克M个城堡并获得里面的宝物. 但由于地理位置原因,有些城堡不能直接攻克,要攻克这些城堡必须先攻克其他某一个特定的城堡.你能帮邱老师算出要获得尽量多的宝物应该攻克哪M个城堡吗? In

UESTC_邱老师选妹子(二) 2015 UESTC Training for Dynamic Programming&lt;Problem I&gt;

I - 邱老师选妹子(二) Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submit Status 邱老师长得帅这是人尽皆知,于是追他的妹子就会很多.但是你知道,邱老师是一个很专一的人,所以他心里面只能有一个人.于是他决定从追他的众多妹子里挑选一个出来. 在第一轮的选拔中,剩余了一些妹子.酱神又给邱老师出主意了,因为最近酱神刚刚学习了最长上升子序列,所以这次,依然是把妹子们

UESTC_最少花费 2015 UESTC Training for Dynamic Programming&lt;Problem D&gt;

D - 最少花费 Time Limit: 30000/10000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submit Status Bob是一个魔法师.这天,他被N座山所阻挡,这些山排成一排,每座山有一个高度.Bob需要从左往右每次跳到相邻的一座山上,相邻的两座山的高度差不能超过K,当从高度差为D的一座山跳到另一座山时要花A×D的魔法值.Bob可以改变一座山的高度,但调整后的高度不能小于0或大于1000,改变S

UESTC_菲波拉契数制 2015 UESTC Training for Dynamic Programming&lt;Problem E&gt;

E - 菲波拉契数制 Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submit Status 我们定义如下数列为菲波拉契数列: F(1)=1 F(2)=2 F(i)=F(i−1)+F(i−2)(i>=3) 给定任意一个数,我们可以把它表示成若干互不相同的菲波拉契数之和.比如13有三种表示法 13=13 13=5+8 13=2+3+8 现在给你一个数n,请输出把它表示成若干互