bzoj1492[NOI2007]货币兑换Cash cdq分治+斜率优化dp
1492: [NOI2007]货币兑换Cash
Time Limit: 5 Sec Memory Limit: 64 MB
Submit: 5541 Solved: 2228
[Submit][Status][Discuss]
Description
.png)
.png)
Input
Output
只有一个实数MaxProfit,表示第N天的操作结束时能够获得的最大的金钱数目。答案保留3位小数。
Sample Input
1 1 1
1 2 2
2 2 3
Sample Output
HINT
.png)
Source
解题的第一个关键是知道每次操作都要完全,即买入就花光所有钱,卖出就卖出所有金券
容易列出暴力方程
f[i]=f[j]/(a[j]*r[j]+b[j])*r[j]*a[i]+f[j]/(a[j]*r[j]+b[j])*b[i]
设x[i]=f[j]/(a[j]*r[j]+b[j])*r[j]
y[i]=f[j]/(a[j]*r[j]+b[j])
f[i]=x[j]*a[i]+y[j]*b[i] 很明显可以斜率优化的式子
假设j比k优 且假设(x[k]<x[j])
那么x[j]*a[i]+y[j]*b[i]>x[k]*a[i]+y[k]*b[i]
=> -a[i]/b[i]<(y[k]-y[j])/(x[k]-x[j]) 维护上凸包
但是
由于-a[i]/b[i]不具有单调性 所以不能够用单调队列维护
由于x[i]不具有单调性 不能用单调队列维护
那么现在只要我们保证了x[i] 和-a[i]/b[i]的单调性,不就可以单调队列维护了?
可以用排序来保证-a[i]/b[i]单调 cdq分治保证x[i]单调且保证在i之前的j都已经转移完毕
#include<bits/stdc++.h>
#define N 100005
using namespace std;
int n,s[N];double f[N];
const double eps=1e-;
const double inf=1e9;
struct query{double a,b,r,k;int id;}q[N],a[N];
struct point{
double x,y;
bool operator < (const point &b)const{
return fabs(x-b.x)<=eps?y<b.y:x<b.x;
}
}p[N],b[N];
double get(int i,int j){
if(fabs(p[i].x-p[j].x)<=eps)return -inf;
return (p[i].y-p[j].y)/(p[i].x-p[j].x);
}
void cdq(int l,int r){
if(l==r){
f[l]=max(f[l],f[l-]);
p[l].y=f[l]/(q[l].a*q[l].r+q[l].b);
p[l].x=p[l].y*q[l].r;return;
}
int mid=l+r>>;
int p1=l,p2=mid+;
for(int i=l;i<=r;i++){
if(q[i].id<=mid)a[p1++]=q[i];
else a[p2++]=q[i];
}
for(int i=l;i<=r;i++)q[i]=a[i];
cdq(l,mid);int tp=;
for(int i=l;i<=mid;i++){
while(tp>&&get(s[tp-],s[tp])<get(s[tp],i))tp--;
s[++tp]=i;
}
int j=;
for(int i=r;i>=mid+;i--){
while(j<tp&&q[i].k<get(s[j],s[j+])+eps)j++;
f[q[i].id]=max(f[q[i].id],p[s[j]].x*q[i].a+p[s[j]].y*q[i].b);
}
cdq(mid+,r);
p1=l,p2=mid+;
for(int i=l;i<=r;i++){
if((p[p1]<p[p2]||p2>r)&&p1<=mid)b[i]=p[p1++];
else b[i]=p[p2++];
}
for(int i=l;i<=r;i++)p[i]=b[i];
} bool cmp(query a,query b){return a.k<b.k;}
int main(){
scanf("%d%lf",&n,&f[]);
for(int i=;i<=n;i++){
scanf("%lf%lf%lf",&q[i].a,&q[i].b,&q[i].r);
q[i].k=-q[i].a/q[i].b;
q[i].id=i;
}
sort(q+,q++n,cmp);
cdq(,n);
printf("%.3lf\n",f[n]);
return ;
}
bzoj1492[NOI2007]货币兑换Cash cdq分治+斜率优化dp的更多相关文章
- [BZOJ1492] [NOI2007] 货币兑换Cash(cdq分治+斜率优化)
[BZOJ1492] [NOI2007] 货币兑换Cash(cdq分治+斜率优化) 题面 分析 dp方程推导 显然,必然存在一种最优的买卖方案满足:每次买进操作使用完所有的人民币:每次卖出操作卖出所有 ...
- BZOJ 1492: [NOI2007]货币兑换Cash [CDQ分治 斜率优化DP]
传送门 题意:不想写... 扔链接就跑 好吧我回来了 首先发现每次兑换一定是全部兑换,因为你兑换说明有利可图,是为了后面的某一天两种卷的汇率差别明显而兑换 那么一定拿全利啊,一定比多天的组合好 $f[ ...
- BZOJ1492:[NOI2007]货币兑换 (CDQ分治+斜率优化DP | splay动态维护凸包)
BZOJ1492:[NOI2007]货币兑换 题目传送门 [问题描述] 小Y最近在一家金券交易所工作.该金券交易所只发行交易两种金券:A纪念券(以下简称A券)和B纪念券(以下简称B券).每个持有金券的 ...
- bzoj 1492: [NOI2007]货币兑换Cash【贪心+斜率优化dp+cdq】
参考:http://www.cnblogs.com/lidaxin/p/5240220.html 虽然splay会方便很多,但是懒得写,于是写了cdq 首先要想到贪心的思路,因为如果在某天买入是能得到 ...
- BZOJ1492: [NOI2007]货币兑换Cash(CDQ分治,斜率优化动态规划)
Description 小Y最近在一家金券交易所工作.该金券交易所只发行交易两种金券:A纪念券(以下简称A券)和 B纪念券(以下 简称B券).每个持有金券的顾客都有一个自己的帐户.金券的数目可以是一个 ...
- 【uoj#244】[UER #7]短路 CDQ分治+斜率优化dp
题目描述 给出 $(2n+1)\times (2n+1)$ 个点,点 $(i,j)$ 的权值为 $a[max(|i-n-1|,|j-n-1|)]$ ,找一条从 $(1,1)$ 走到 $(2n+1,2n ...
- BZOJ 1492 [NOI2007]货币兑换Cash (CDQ分治/splay 维护凸包)
题目大意:太长了略 splay调了两天一直WA弃疗了 首先,我们可以猜一个贪心,如果买/卖,就一定都买/卖掉,否则不买/卖 反正货币的行情都是已知的,没有任何风险,所以肯定要选择最最最优的方案了 容易 ...
- bzoj3672/luogu2305 购票 (运用点分治思想的树上cdq分治+斜率优化dp)
我们都做过一道题(?)货币兑换,是用cdq分治来解决不单调的斜率优化 现在它放到了树上.. 总之先写下来dp方程,$f[i]=min\{f[j]+(dis[i]-dis[j])*p[i]+q[i]\} ...
- BZOJ 3963: [WF2011]MachineWorks [CDQ分治 斜率优化DP]
传送门 当然了WF的题uva hdu上也有 你的公司获得了一个厂房N天的使用权和一笔启动资金,你打算在这N天里租借机器进行生产来获得收益.可以租借的机器有M台.每台机器有四个参数D,P,R,G.你可以 ...
随机推荐
- 关于mule中使用jdbc时报No Suitable Driver found错误的问题
错误大概信息: Exception in thread "main" org.mule.module.launcher.DeploymentStartException: SQLE ...
- 2017 清北济南考前刷题Day 3 afternoon
期望得分:100+40+100=240 实际得分:100+40+100=240 将每个联通块的贡献乘起来就是答案 如果一个联通块的边数>点数 ,那么无解 如果边数=点数,那么贡献是 2 如果边数 ...
- maven入门(1-1)maven是什么?
Maven是一个项目管理工具,它包含了 一个项目对象模型 (Project Object Model), 一组标准集合, 一个项目生命周期(Project Lifecycle), 一个依赖管理系统(D ...
- bootstrap 菜单之手风琴效果
自己用bootstrap搭了个项目,纯属娱乐....为了检验学习bootstrap之成果. 效果如图: 一.搭建中发现一问题,因为以前测试都是写的html页面,这次用了母版页,点击页面的之后,页面会刷 ...
- Python入门之函数的嵌套/名称空间/作用域/函数对象/闭包函数
本篇目录: 一.函数嵌套 二.函数名称空间与作用域 三.函数对象 四.闭包函数 ============================================================ ...
- js常用的数组方法
1.创建数组的基本方法: 1.1 空数组 var obj=new Array(); 1.2 指定长度数组 var obj=new Array(size); ...
- Hive函数:LAG,LEAD,FIRST_VALUE,LAST_VALUE
参考自大数据田地:http://lxw1234.com/archives/2015/04/190.htm 测试数据准备: create external table test_data ( cooki ...
- React-Native(五):React Native之Text学习
本章节主要学习Text的布局,仿照网易新网: 代码: /** * Sample React Native App * https://github.com/facebook/react-native ...
- urlopen()&urlretrieve()
1.urlopen()方法 urllib.request.urlopen(url[,data[,proxies]]) 创建一个表示远程url的类文件对象,然后像本地文件一样的操作这个类文件对象来获取远 ...
- 简述angular自定义过滤器在页面和控制器中的使用
首先设置自定义过滤器. 定义模块名:angular ? 1 2 3 4 5 6 .module('myApp') .filter('filterName',function(){ return fun ...