ZOJ 3469 Food Delivery -- 区间dp
2015-07-21 09:44
507 查看
题目链接点击打开链接
题意:一条直线上有n个人点外卖。每个人都有一个坐标xi。每个人都有一个不开心值,每过一秒不开心值增加一倍,初始值都为0。外卖小哥初始在点x上,以速度v-1给这直线上的n个人送外卖。求不开心值总和最少多少。
思路:区间dp。这是一类当前决策对未来有影响的dp,方法是将当前决策对未来的影响直接加到当前。
dp[i][j][0]表示区间i到j且停在i点的最小值,dp[i][j][1]表示间i到j且停在j点的最小值。令sum[i]表示从点1到点i的不开心值总和。
dp[i][j][0] = min(dp[i][j][0],dp[i+1][j][0]+(a[i+1].x-a[i].x)*(sum[i]+sum
-sum[j]);
dp[i][j][0] = min(dp[i][j][0],dp[i+1][j][1]+(a[j].x-a[i].x)*(sum[i]+sum
-sum[j]);
dp[i][j][1] = min(dp[i][j][1],dp[i][j-1][0]+(a[j].x-a[i].x)*(sum[i-1]+sum
-sum[j-1]);
dp[i][j][1] = min(dp[i][j][1],dp[i][j-1][1]+(a[j].x-a[j-1].x)*(sum[i-1]+sum
-sum[j-1]);
最终结果为 min(dp[i][j][0],dp[i][j][1])*(v-1)。
AC代码
题意:一条直线上有n个人点外卖。每个人都有一个坐标xi。每个人都有一个不开心值,每过一秒不开心值增加一倍,初始值都为0。外卖小哥初始在点x上,以速度v-1给这直线上的n个人送外卖。求不开心值总和最少多少。
思路:区间dp。这是一类当前决策对未来有影响的dp,方法是将当前决策对未来的影响直接加到当前。
dp[i][j][0]表示区间i到j且停在i点的最小值,dp[i][j][1]表示间i到j且停在j点的最小值。令sum[i]表示从点1到点i的不开心值总和。
dp[i][j][0] = min(dp[i][j][0],dp[i+1][j][0]+(a[i+1].x-a[i].x)*(sum[i]+sum
-sum[j]);
dp[i][j][0] = min(dp[i][j][0],dp[i+1][j][1]+(a[j].x-a[i].x)*(sum[i]+sum
-sum[j]);
dp[i][j][1] = min(dp[i][j][1],dp[i][j-1][0]+(a[j].x-a[i].x)*(sum[i-1]+sum
-sum[j-1]);
dp[i][j][1] = min(dp[i][j][1],dp[i][j-1][1]+(a[j].x-a[j-1].x)*(sum[i-1]+sum
-sum[j-1]);
最终结果为 min(dp[i][j][0],dp[i][j][1])*(v-1)。
AC代码
#include<iostream> #include<cstdio> #include<cstring> #include<stack> #include <algorithm> #include <cmath> using namespace std; const int N = 1015; const int INF = 0x3f3f3f3f; typedef long long LL; struct node { int x,b; } a ; bool cmp(node aa,node b) { return aa.x<b.x; } int dp [2],sum ; ///dp[i][j][0] means end at the left ///dp[i][j][1] means end at the right int main() { int n,v,x,sta; while(scanf("%d%d%d",&n,&v,&x)==3) { for(int i=1; i<=n; i++) scanf("%d%d",&a[i].x,&a[i].b); n++; a .x = x,a .b = 0; sort(a+1,a+n+1,cmp); sum[0] = 0; for(int i = 1; i<=n; i++) { sum[i] = sum[i-1] + a[i].b; if(a[i].x == x) { sta = i; } } for(int i=0; i<=n; i++) for(int j=0; j<=n; j++) dp[i][j][0] = dp[i][j][1] = INF; dp[sta][sta][0] = dp[sta][sta][1] = 0; for(int i=sta; i>=1; i--) { for(int j=i+1; j<=n; j++) { // if(i==j) continue; ///end at left dp[i][j][0] = min(dp[i][j][0],dp[i+1][j][0]+(sum -sum[j]+sum[i])*(a[i+1].x-a[i].x)); dp[i][j][0] = min(dp[i][j][0],dp[i+1][j][1]+(sum -sum[j]+sum[i])*(a[j].x-a[i].x)); ///end at right dp[i][j][1] = min(dp[i][j][1],dp[i][j-1][0]+(sum -sum[j-1]+sum[i-1])*(a[j].x-a[i].x)); dp[i][j][1] = min(dp[i][j][1],dp[i][j-1][1]+(sum -sum[j-1]+sum[i-1])*(a[j].x-a[j-1].x)); } } printf("%d\n",v*min(dp[1] [0],dp[1] [1])); } return 0; }
相关文章推荐
- Maven打war包出错
- 快速复制电脑C盘——轻松备份系统
- 表单验证插件jquery.validate的使用方法演示
- iOS之友盟错误统计解决
- hdu 1561 树形dp
- dl-ssl.google.com
- Android Binder详解
- nodejs升级,npm升级
- 【mysql】如何做到表内存在同名字段就更改记录,不存在就新增记录(replace的详细使用)
- Pig的安装和使用方法
- 转载:JSONObject.fromObject(map)(JSON与JAVA数据的转换)
- Linux下配置一个VNC服务器
- VC++ 多线程模拟鼠标点击
- 安装YII2
- 黑马程序员——Java交通灯管理系统&银行业务系统
- git pro 笔记
- uncaught exception 'CALayerInvalidGeometry', reason: 'CALayer bounds contains NaN: [nan 0; 600 300]'
- zoj 2158 Truck History
- java的常量池问题
- IOS本地推送 学习手记