HYSBZ-1067 降雨量 RMQ

来源:互联网 发布:js匿名函数 编辑:程序博客网 时间:2024/06/11 10:41

我们常常会说这样的话:“X年是自Y年以来降雨量最多的”。它的含义是X年的降雨量不超过Y年,且对于任意
Y<Z<X,Z年的降雨量严格小于X年。例如2002,2003,2004和2005年的降雨量分别为4920,5901,2832和3890,
则可以说“2005年是自2003年以来最多的”,但不能说“2005年是自2002年以来最多的”由于有些年份的降雨量未
知,有的说法是可能正确也可以不正确的。

Input
  输入仅一行包含一个正整数n,为已知的数据。以下n行每行两个整数yi和ri,为年份和降雨量,按照年份从小
到大排列,即yi<yi+1。下一行包含一个正整数m,为询问的次数。以下m行每行包含两个数Y和X,即询问“X年是
自Y年以来降雨量最多的。”这句话是必真、必假还是“有可能”。

Output
  对于每一个询问,输出true,false或者maybe。

Sample Input
6
2002 4920
2003 5901
2004 2832
2005 3890
2007 5609
2008 3024
5
2002 2005
2003 2005
2002 2007
2003 2007
2005 2008
Sample Output
false
true
false
maybe
false

Hint
100%的数据满足:1<=n<=50000, 1<=m<=10000, -10^9<=yi<=10^9, 1<=ri<=10^9
题解:
求区间最大值问题
对于每个询问(a,b)
1. 如果 a ,b降雨量知道
①a,b 中间年份降雨量全部知道
②a,b 中间年份降雨量部分不知道
2. a 或b降雨量不知道
① a 和 b 降雨量都不知道 直接输出maybe
② a 降雨量不知道
③ b 降雨量不知道

代码:

#include <iostream>#include <string>#include <cstring>#include <cstdio>#include <cmath>#include <cstdlib>#include <algorithm>#include <queue>#include <map>#define MST(s,q) memset(s,q,sizeof(s))#define INF 0x3f3f3f3f#define MAXN 100005#define Lchild id<<1#define Rchild (id<<1)+1using namespace std;map<int , int>mp;int Year[MAXN], pos[MAXN], N, M,  a, b, mx[MAXN][20];char answer[3][10] = {"false", "true", "maybe"};void init(int n) {    for (int i = 1; i <= n; i++)        mx[i][0] = Year[i];    for (int j = 1; (1 << j) <= n; j++)        for (int i = 1; i + (1 << j) - 1 <= n; i++)            mx[i][j] = max(mx[i][j - 1], mx[i + (1 << (j - 1))][j - 1]);}int RMQ(int i, int j) {    if (j < i) return -1;    int k = (int)(log(j - i + 1) / log(2));    return max(mx[i][k], mx[j - (1 << k) + 1][k]);}int main() {    cin >> N;    for (int i = 1; i <= N; i++) {        scanf("%d%d", &pos[i], &Year[i]);  // 年份存在pos数组里,降水量存在Year里        mp[pos[i]] = i;    }    init(N);    cin >> M;    while (M--) {        scanf("%d%d", &a, &b);        int p1 = mp[a], p2 = mp[b], ans = 0;        if (p1 == 0 || p2 == 0) {     //  a 或 b 的降水量不知            if (p1 == 0 && p2 == 0) {printf("maybe\n"); continue;}  //  a 和 b 的降水量不知            int  L = lower_bound(pos + 1, pos + 1 + N, a) - pos;            int  R = lower_bound(pos + 1, pos + 1 + N, b) - pos;            if (p1 == 0 && RMQ(L, R - 1) < Year[R])   //  a  的降水量不知                ans = 2;            else if (p2 == 0 && RMQ(L + 1, R - 1) < Year[L] ) //  a  的降水量不知                ans = 2;        }        else if (p2 - p1 == b - a) {     //  from a to b 全部知道            if (Year[p2] <= Year[p1] && RMQ(p1 + 1, p2 - 1) < Year[p2] )                ans = 1;        }        else {       // from a to b 存在某年不知道            if (Year[p2] <= Year[p1] && RMQ(p1 + 1, p2 - 1) < Year[p2] )                ans = 2;        }        printf("%s\n", answer[ans] );    }}
0 0
原创粉丝点击