首页 > 其他分享 >P3957 [NOIP2017 普及组] 跳房子

P3957 [NOIP2017 普及组] 跳房子

时间:2024-03-06 19:44:38浏览次数:35  
标签:NOIP2017 跳房子 return room ll 最大值 sum P3957

原题链接

题解

二分加动态维护区间最大值
注意设立变量的含义,改变变量值的规则

code

#include<bits/stdc++.h>
#define ll long long
using namespace std;
ll sum[500005]={0};
struct unit
{
    ll x,v;
    bool operator <(const unit &b) const{return b.v>v;}//
}room[500005];

ll n,d,k;
ll check(ll g)
{
    memset(sum,-0x3f,sizeof sum);//初始化,由于分数有负,所以赋无限小为未踏入
    sum[0]=0;//如果一步也不走,得到的分数为零

    priority_queue<unit> q;//维护的是线性改变区间内的最大值
    //不能初始放入00,因为虽然放入其他值的时候确保了距离大于d-g,但是零点没有,这就导致了q中违规出现了小于d-g的值0
    ll it=0;
    for(ll i=1;i<=n;i++)//遍历房子
    {
        while(it<i&&room[i].x-room[it].x>=max(1LL,d-g)) q.push({room[it].x,sum[it++]});//可以从哪个房子跳过来,细节,由于要求跳的长度至少为一,所以当d-g小于1的时候要判断
        //但是由于有it<i和递增输入的限制,这个不会触发错误
        //这里添加要放在删除前面,因为刚添加进去的不一定小于d+g,他只是小于前一个点的d+g
        while(q.size()&&room[i].x-q.top().x>d+g) q.pop();

        if(q.size()) sum[i]=max(sum[i],q.top().v+room[i].v);//经过删除和添加后,堆顶是最大值
        //printf("sum[%d] = %d\n",i,sum[i]);
        if(sum[i]>=k)return 1;
    }
    return 0;
}
int main()
{
    cin>>n>>d>>k;

    for(ll i=1;i<=n;i++)  cin>>room[i].x>>room[i].v;//输入为升序

    room[0].x=0;
    ll l=-1,r=1e9+2;

    while(l<r-1)
    {
        ll mid=(l+r)/2;
        //printf("%d\n",mid);
        if(check(mid)) r=mid;
        else l=mid;
        //puts("\n");
    }

    if(l!=1e9+1) cout<<r<<endl;
    else puts("-1");//只有一次大于k都没有才会等于1e9+1
    return 0;
}

标签:NOIP2017,跳房子,return,room,ll,最大值,sum,P3957
From: https://www.cnblogs.com/pure4knowledge/p/18057390

相关文章

  • P3958 [NOIP2017 提高组] 奶酪
    原题链接思路并查集然后看看是否存在上表面联通的洞与下表面联通的洞位于同一集合code#include<bits/stdc++.h>usingnamespacestd;doublen,h,r;intfa[1005];vector<int>up,down;struct{doublex,y,z;}hole[1005];doubledis(inti,intj){returnpo......
  • P3957 [NOIP2017 普及组] 跳房子
    50分代码1//P3957[NOIP2017普及组]跳房子2#include<iostream>3#include<queue>4#include<cstring>5#include<cmath>6usingnamespacestd;7typedeflonglongll;8intn,d,k;9inta[500010][2];10llf[500010],sum=0;11boo......
  • 算法题:跳房子问题(爬楼梯问题进阶) 求解受限制情况下的方案数目
    问题跳房子,规定总共有n个格子,每次可以选择跳1个格子、2个格子或3个格子,但是下一步不能和当前选择的跳跃距离一样,计算总共有多少种跳房子方案。分析这就是经典爬楼梯问题的进阶,仅仅换了个说法,但是比经典的爬楼梯问题难了不少,传统的爬楼梯问题一次可以上1或2个台阶没有连续动作......
  • P3953 [NOIP2017 提高组] 逛公园
    Description策策同学特别喜欢逛公园。公园可以看成一张\(N\)个点\(M\)条边构成的有向图,且没有自环和重边。其中\(1\)号点是公园的入口,\(N\)号点是公园的出口,每条边有一个非负权值,代表策策经过这条边所要花的时间。策策每天都会去逛公园,他总是从\(1\)号点进去,从\(N\)......
  • P3956 [NOIP2017 普及组] 棋盘
    传送门P3956[NOIP2017普及组]棋盘不清楚曾师为什么把这个神奇的题目放在搜索\(search\)专栏,反正我用\(dijkstra\)水过去了,虽然\(dijkstra\)严格来说也是一种能够解决一般性最短路问题的算法。然后考虑这道题的建图。这道题来看首先是去除魔法的部分,一般地,任意一个点只......
  • NOIP2017提高组初赛易错题解析
     8.由四个不同的点构成的简单无向连通图的个数是()A.32 B.35 C.38 D.41错误原因:数重了正解:分情况计算,6条边的有1种,5条边的有C(6,1)=6种,4条边的有C(6,4)=15种,3条边,要分度数,2+2+1+1的有12种,3+1+1+1的有4种,共38种 10.若 f0​=0,f1​=1,fn+1​=(fn​+fn−1)/2​​,则随着......
  • 「NOIP2017 普及组」棋盘 题解
    前言一个绿题,风光啊QwQ题面传送门思路怎么走我们定义一个函数dfs(x,y,coin,can,color)x,y表示坐标,coin表示当前的金币数量,color表示当前坐标的颜色,can表示当前是否能施展魔法。再加一个mp数组记录颜色,-1表示无颜色,0表示红色,1表示黄色为什么不直接使用mp[x][y]获取颜......
  • 6312: 河中跳房子 二分
    描述 每年奶牛们都要举办各种特殊版本的跳房子比赛,包括在河里从一个岩石跳到另一个岩石。这项激动人心的活动在一条长长的笔直河道中进行,在起点和离起点L远(1≤L≤1,000,000,000)的终点处均有一个岩石。在起点和终点之间,有N(0≤N≤50,000)个岩石,每个岩石与起点的距......
  • 【题解】[NOIP2017 提高组] 逛公园
    题目描述:策策同学特别喜欢逛公园。公园可以看成一张\(N\)个点\(M\)条边构成的有向图,且没有自环和重边。其中\(1\)号点是公园的入口,\(N\)号点是公园的出口,每条边有一个非负权值,代表策策经过这条边所要花的时间。策策每天都会去逛公园,他总是从\(1\)号点进去,从\(N\)号......
  • P3954 [NOIP2017 普及组] 成绩
    [NOIP2017普及组]成绩题目背景NOIP2017普及组T1题目描述牛牛最近学习了C++入门课程,这门课程的总成绩计算方法是:总成绩=作业成绩$\times20%+$小测成绩$×30%+$期末考试成绩$\times50%$牛牛想知道,这门课程自己最终能得到多少分。输入格式三个非负整数$A,B,C$,分别......