• 【题解】[SCOI2007]降雨量


    原题链接

    这题调了我快一个小时,在此记录下这题的坑点。

    备注:$A$ 无数据指的是 $A$ 年份没有雨量记录;$A sim B$ 指 $A$ 年到 $B$ 年间(包括 $A,B$)的所有年份。

    • $X,Y$ 都无数据的情况下,答案必为 maybe
    • $X$ 无数据的情况下,需要判断 $Y+1 sim X$ 中有数据的年份是否大于等于 $Y$ 年的雨量,是输出 false,不是输出 maybe
    • $Y$ 无数据的情况下
      • 若 $X$ 比所有年份都早,则数据全无,直接输出 maybe
      • 否则判断 $Y sim X-1$ 中有数据的年份是否大于等于 $X$ 年的雨量,是输出 false,不是输出 maybe
    • 其余情况
      • 判断 $Y+1 sim X$ 中有数据的年份是否不等于 $Y$ 年的雨量,是输出 false
      • 判断 $Y+1 sim X-1$ 中有数据的年份是否等于 $X$ 年的雨量,是输出 false
      • 判断 $X$ 年的雨量是否大于 $Y$ 年的雨量,是输出 false
      • 判断 $X sim Y$ 间是否每年都记录了数据,是输出 true,否则 maybe

    其它没什么好说的,线段树维护最值,map 或离散化解决年份值域问题。

    代码如下:

    #include <algorithm>
    #include <cstdio>
    #include <map>
    #define INF 1e9
    #define eps 1e-6
    typedef long long ll;
    using namespace std;
    
    map <int, int> m;
    int n, q, y[50010], R[50010], maxx[200010];
    
    inline int max(int a, int b){
        return a > b ? a : b;
    }
    
    void build(int i, int l, int r){
        if(l == r){
            maxx[i] = R[l];
            return;
        }
        int mid = (l + r) >> 1;
        build(i << 1, l, mid);
        build(i << 1 | 1, mid + 1, r);
        maxx[i] = max(maxx[i << 1], maxx[i << 1 | 1]);
    }
    
    int query(int i, int l, int r, int x, int y){
        if(l > r) return 0;
        if(l >= x && r <= y) return maxx[i];
        int ss = 0, mid = (l + r) >> 1;
        if(x <= mid) ss = max(ss, query(i << 1, l, mid, x, y));
        if(y > mid) ss = max(ss, query(i << 1 | 1, mid + 1, r, x, y));
        return ss;
    }
    
    int main(){
    
        scanf("%d", &n);
        for(int i = 1; i <= n; i++)
            scanf("%d%d", &y[i], &R[i]), m[y[i]] = i;
        build(1, 1, n);
        scanf("%d", &q);
        for(int i = 1, X, Y, pos, poss; i <= q; i++){
            scanf("%d%d", &X, &Y);
            pos = lower_bound(y + 1, y + n + 1, X) - y;
            if(!m[X] && !m[Y]) puts("maybe");
            else if(!m[Y]){
                poss = lower_bound(y + 1, y + n + 1, Y) - y - 1;
                if(query(1, 1, n, pos + 1, poss) >= R[m[X]]) puts("false");
                else puts("maybe");
            }
            else if(!m[X]){
                if(m[Y] == 1) puts("maybe");
                else if(query(1, 1, n, pos, m[Y] - 1) >= R[m[Y]]) puts("false");
                else puts("maybe");
            }
            else{
                if(query(1, 1, n, pos + 1, m[Y]) != R[m[Y]]) puts("false");
                else if(query(1, 1, n, pos + 1, m[Y] - 1) == R[m[Y]]) puts("false");
                else if(query(1, 1, n, pos + 1, m[Y] - 1) >= R[m[X]]) puts("false");
                else if(R[m[Y]] > R[m[X]]) puts("false");
                else if(Y - X != m[Y] - m[X]) puts("maybe");
                else puts("true");
            }
        }
    
        return 0;
    }
  • 相关阅读:
    应急响应之如何发现隐藏的Webshell后门
    从失败终止到崩溃
    DumpConfigurator Utility工具
    使例外成为例外(而不是异常)
    用于可视化虚拟内存使用情况和GC堆使用情况的工具。
    关于EEMessageException异常
    c#/C++混合编程的一个问题
    关于std::__non_rtti_object异常
    仅通过转储来排除内存泄漏
    调试器不应该改变行为
  • 原文地址:https://www.cnblogs.com/zengpeichen/p/14806617.html
Copyright © 2020-2023  润新知