poj 3246 简单线段树

线段树还真有点难写。。。

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <stack>
#include <queue>

using namespace std;
typedef long long LL;
#define oo 0x3f3f3f3f
#define N 200100

struct node
{
    int l, r;
    int s, e;
} tree[N*4];

int A[N];

void build(int l, int r, int rt)
{
    tree[rt].l=l;
    tree[rt].r=r;
    if(l==r)
    {
        tree[rt].s=tree[rt].e=A[l];
        return ;
    }
    int mid;
    mid=(l+r)/2;
    build(l, mid, rt*2);
    build(mid+1, r, rt*2+1);
    tree[rt].s=max(tree[rt*2].s, tree[rt*2+1].s);
    tree[rt].e=min(tree[rt*2].e, tree[rt*2+1].e);

    return ;
}

int query(int l, int r, int rt)
{
    if(tree[rt].l>=l&&tree[rt].r<=r)
    {
        return tree[rt].s;
    }
    int mid=(tree[rt].l+tree[rt].r)/2;
    if(r<=mid) return query(l, r, rt*2);
    else if(l>mid) return query(l, r, rt*2+1);
    else
    {
        return max(query(l, mid, rt*2), query(mid+1, r, rt*2+1));
    }
}

int Query(int l, int r, int rt)
{
    if(tree[rt].l>=l&&tree[rt].r<=r)
    {
        return tree[rt].e;
    }
    int mid=(tree[rt].l+tree[rt].r)/2;
    if(r<=mid) return Query(l, r, rt*2);
    else if(l>mid) return Query(l, r, rt*2+1);
    else
    {
        return min(Query(l, mid, rt*2), Query(mid+1, r, rt*2+1));
    }
}

int main()
{
    int n, m, a, b;

    while(~scanf("%d%d", &n, &m))
    {
        for(int i=1; i<=n; i++)
            scanf("%d", &A[i]);
        build(1, n, 1);

        while(m--)
        {
            scanf("%d%d", &a, &b);
            printf("%d
", query(a, b, 1)-Query(a, b, 1));
        }
    }
    return 0;
}
原文地址:https://www.cnblogs.com/9968jie/p/5661433.html