传送门


仍然对“为什么这个函数单峰”的问题毫无理解

首先,对于保质期又低、价格又贵的食物,我们显然不需要购买它。所以如果设\(pri_i\)表示保质期不小于\(i\)的所有食品中价格最低的食品的价格,那么\(pri\)数组显然单调不降。

考虑如果我们要直接去做比较麻烦,可是如果我们知道点外卖的次数,就很好计算了。

假设我们知道了我们总共要买\(x\)次外卖,不难知道这\(x\)次外卖点的食物能够坚持的时间的极差不会超过\(1\),否则可以用多的补少的,在不降低总坚持时间的情况下降低总价格(因为\(pri\)单调不降)。

假设\(x\)次外卖坚持的时间为\(K\)与\(K+1\),那么可以先二分出\(K\),然后将剩下的钱尽可能多的买\(pri_{K+1}\)。

现在,确定点外卖的次数就可以求得对应的能够坚持的时间,问题就是如何求最长的时间。不难发现点外卖的次数与坚持的时间对应的函数是一个单峰函数,直接上三分就完事了。

有没有神仙会证这个函数单峰啊QAQ

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<ctime>
#include<cctype>
#include<algorithm>
#include<cstring>
#include<iomanip>
#include<queue>
#include<map>
#include<set>
#include<bitset>
#include<stack>
#include<vector>
#include<cmath>
#define INF 0x3f3f3f3f
#define int long long
#define PII pair < int , int >
#define st first
#define nd second
//This code is written by Itst
using namespace std; inline int read(){
int a = 0;
char c = getchar();
bool f = 0;
while(!isdigit(c) && c != EOF){
if(c == '-')
f = 1;
c = getchar();
}
if(c == EOF)
exit(0);
while(isdigit(c)){
a = (a << 3) + (a << 1) + (c ^ '0');
c = getchar();
}
return f ? -a : a;
} vector < PII > tg;
vector < PII > :: iterator it , it1;
int M , F , N , sum[210];
bool f[210]; inline int calcSum(int dir){
it = lower_bound(tg.begin() , tg.end() , PII(dir , -1));
int t = it - tg.begin();
if(t && !f[t - 1] || (t ? sum[t - 1] : 0) + 1.0 * tg[t].nd * (dir - (t ? tg[t - 1].st : -1)) > M)
return 2e18;
return (t ? sum[t - 1] : 0) + tg[t].nd * (dir - (t ? tg[t - 1].st : -1));
} inline int calc(int x){
int s = M - x * F , L = -1 , R = tg[N - 1].st;
while(L < R){
int mid = L + R + 1 >> 1;
calcSum(mid) <= s / x ? L = mid : R = mid - 1;
}
s -= calcSum(L) * x;
if(L == tg[N - 1].st)
return (L + 1) * x;
it = lower_bound(tg.begin() , tg.end() , PII(L + 1 , -1));
return (L + 1) * x + s / it->second;
} inline bool check(int mid){
return calc(mid) >= calc(mid + 1);
} signed main(){
#ifndef ONLINE_JUDGE
//freopen("in" , "r" , stdin);
//freopen("out" , "w" , stdout);
#endif
M = read();
F = read();
N = read();
for(int i = 1 ; i <= N ; ++i){
int a = read() , b = read();
tg.push_back(PII(b , a));
}
sort(tg.begin() , tg.end());
for(it = --tg.end() , it1 = it , --it1 ; it != tg.begin() ; --it , it1 = it , --it1)
if(it->nd < it1->nd)
it1->nd = it->nd;
for(it = tg.begin() , it1 = it , ++it1 ; it1 != tg.end() ; ++it , it1 = it , ++it1)
if(it->st == it1->st)
it1->nd = it->nd;
for(int i = 0 ; i < N ; ++i)
if((i == 0 ? 0 : sum[i - 1]) + 1.0 * tg[i].nd * (tg[i].st - (i == 0 ? -1 : tg[i - 1].st)) <= M){
f[i] = 1;
sum[i] = (!i ? 0 : sum[i - 1]) + tg[i].nd * (tg[i].st - (!i ? -1 : tg[i - 1].st));
}
else
break;
int L = 1 , R = M / F;
while(L < R){
int mid = (L + R) >> 1;
check(mid) ? R = mid : L = mid + 1;
}
cout << calc(L);
return 0;
}

Luogu4040 AHOI/JSOI2014 宅男计划 贪心、二分、三分的更多相关文章

  1. 【BZOJ3874】[AHOI&JSOI2014]宅男计划(贪心,三分)

    [BZOJ3874][AHOI&JSOI2014]宅男计划(贪心,三分) 题面 BZOJ 洛谷 题解 大力猜想一最长的天数和购买外卖的总次数是单峰的.感性理解一下就是买\(0\)次是\(0\) ...

  2. 洛谷$P4040\ [AHOI2014/JSOI2014]$宅男计划 贪心

    正解:三分+贪心 解题报告: 传送门$QwQ$ 其实很久以前的寒假就考过了,,,但那时候$gql$没有好好落实,就只写了个二分,并没有二分套三分,就只拿到了$70pts$ #include <b ...

  3. [luogu] P4040 [AHOI2014/JSOI2014]宅男计划(贪心)

    P4040 [AHOI2014/JSOI2014]宅男计划 题目背景 自从迷上了拼图,JYY就变成了个彻底的宅男.为了解决温饱问题,JYY不得不依靠叫外卖来维持生计. 题目描述 外卖店一共有N种食物, ...

  4. Bzoj 3874: [Ahoi2014&Jsoi2014]宅男计划 三分+贪心

    3874: [Ahoi2014&Jsoi2014]宅男计划 Time Limit: 1 Sec  Memory Limit: 256 MBSubmit: 861  Solved: 336[Su ...

  5. bzoj3874&2832 [Ahoi2014]宅男计划 模拟退火,三分

    [Ahoi2014&Jsoi2014]宅男计划 Time Limit: 1 Sec  Memory Limit: 256 MBSubmit: 962  Solved: 371[Submit][ ...

  6. BZOJ3874:[AHOI2014&JSOI2014]宅男计划(爬山法)

    Description  [故事背景] 自从迷上了拼图,JYY就变成了个彻底的宅男.为了解决温饱问题,JYY 不得不依靠叫外卖来维持生计. [问题描述] 外卖店一共有N种食物,分别有1到N编号.第i种 ...

  7. bzoj 3874: [Ahoi2014&Jsoi2014]宅男计划

    Description 外卖店一共有N种食物,分别有1到N编号.第i种食物有固定的价钱Pi和保质期Si.第i种食物会在Si天后过期.JYY是不会吃过期食物的. 比如JYY如果今天点了一份保质期为1天的 ...

  8. food(洛谷P4040 [AHOI2014/JSOI2014]宅男计划)

    题目在这里 题目描述 外卖店一共有N种食物,分别有1到N编号.第i种食物有固定的价钱Pi和保质期Si.第i种食物会在Si天后过期.JYY是不会吃过期食物的. 比如JYY如果今天点了一份保质期为1天的食 ...

  9. Luogu P4040 [AHOI2014/JSOI2014]宅男计划

    题目 显然存活天数与叫外卖次数的函数是凸函数. 所以三分买外卖的次数. 然后把食品按保质期升序排序. 并且单调栈搞一下,把又贵又保质期短的丢掉. 那么随着保质期的增加,食品的价格一定上涨. 所以我们从 ...

随机推荐

  1. 函数节流scroll,兼容火狐滚轮事件

    //函数节流 var wheelTimeout; var wheelFun = function (func) { if (wheelTimeout) { return; } func(); whee ...

  2. Mybatis PageHelper 简单使用

    流程 1,maven 依赖 2,在 mybatis 配置文件启用插件 3,修改 service 层 依赖 <!-- https://mvnrepository.com/artifact/com. ...

  3. 在Visualforce页面中使用Visual Flow

    在本文中,我们将通过一个示例说明如何将"流"(Visual Flow)用于Visualforce页面. 更全面的知识可以参考官方文档. 创建流 我们要创建一个流,它的作用是得到一个 ...

  4. BI怎么选?重点看这10个技术指标

    2016年,商业智能市场火热,不管是投资圈还是IT圈,都在广泛关注着大数据和商业智能.宣传广告媒体报道见多了,不知道大家对BI选型的技术标准有谱了没.笔者对Gartner的BI魔力象限考评的15个关键 ...

  5. (网页)readonly和disabled的区别(转)

    转自脚本之家: 标签的readonly和disabled属性的区别: 在表单元素中,readonly和disable有类似之处,因为它们都可以将一些表单元素设置为"不可用"状态,当 ...

  6. 13.2、进程的通信:Queue、Pipe、

    内容相关: 概念:进程的通信 Queue:创建与使用 Pipe:创建与使用 进程通信的概念 进程的资源空间是相互独立的,一般而言是不能相互访问的.但很多情况下进程间需要互相通信,来完成系统的某项功能. ...

  7. 《R数据挖掘入门》彩色插图(第8章)

    图8.4 图8.5 图8.6 图8.7

  8. SSO阅读有感

    SSO比较详细且理解.赞 链接:https://www.cnblogs.com/ywlaker/p/6113927.html

  9. 无需软件windows如何加密文件夹

    在百部百科上看到,放在博客中以便查看. 1.首先打开记事本,当然如果你的电脑里装有类似notepad++的文本编辑软件的也可以,但是不能用word.用这类软件好处是代码高亮,看上去舒服,减少错误率. ...

  10. QSetting的值不能保存。

    最近在使用QSetting的时候,setting的值死活保存不下来,后来添加了如何设置后,settting的可以获取到. QCoreApplication::setOrganizationName(& ...