比赛 EYOI与SBOI开学欢乐赛1st 评测结果 AAAAAAAAAA
题目名称 双倍腹肌量 最终得分 100
用户昵称 yrtiop 运行时间 0.563 s
代码语言 C++ 内存使用 13.28 MiB
提交时间 2022-08-29 21:06:08
显示代码纯文本
#include <bits/stdc++.h>
const int maxn = 1e5 + 5;
const int INF = 1e9;

int n,m,f[maxn][20],dp[maxn][20],lg[maxn];
struct node {
    int x,y;
    node() {
        x = y = 0;
    }
}a[maxn];

int RMQmin(int l,int r) {
    int k = lg[r - l + 1];
    return std::min(dp[l][k] , dp[r - (1 << k) + 1][k]);
}

int RMQmax(int l,int r) {
    int k = lg[r - l + 1];
    return std::max(f[l][k] , f[r - (1 << k) + 1][k]);
}

int main() {
    freopen("double_muscle.in","r",stdin);
    freopen("double_muscle.out","w",stdout);
    scanf("%d %d",&n,&m);
    for(int i = 1;i <= n;++ i) {
        scanf("%d %d",&a[i].x,&a[i].y);
    }
    
    std::sort(a + 1 , a + 1 + n , [&](const node& p,const node& q) {
        return p.x < q.x;
    });
    for(int i = 1;i <= n;++ i)f[i][0] = dp[i][0] = a[i].y;
    for(int i = 2;i <= n;++ i)lg[i] = lg[i >> 1] + 1;
    for(int k = 1;(1 << k) <= n;++ k) {
        for(int i = 1;i + (1 << k) - 1 <= n;++ i) {
            f[i][k] = std::max(f[i][k - 1] , f[i + (1 << k - 1)][k - 1]);
            dp[i][k] = std::min(dp[i][k - 1] , dp[i + (1 << k - 1)][k - 1]);
        }
    }
    
    int ans = INF;
    for(int i = 1,l = 1;i <= n;++ i) {
        for(;l < i&&RMQmax(l + 1 , i) - RMQmin(l + 1 , i) >= m;++ l);
        if(RMQmax(l , i) - RMQmin(l , i) >= m)ans = std::min(ans , a[i].x - a[l].x);
    }
    
    printf("%d\n",(ans ^ INF) ? ans : -1);
    return 0;
}