Cod sursa(job #934539)

Utilizator a_h1926Heidelbacher Andrei a_h1926 Data 30 martie 2013 19:35:42
Problema Range minimum query Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 1.61 kb
#include <cstdio>
#include <cstring>
#include <cassert>

#include <iostream>
#include <fstream>
#include <algorithm>
#include <vector>
#include <string>
#include <queue>

using namespace std;

typedef long long int64;
typedef vector<int>::iterator it;

const int oo = 0x3f3f3f3f;
const int MAX_N = 100005;
const int MAX_LOG = 17;

int N, Values[MAX_N], RMQ[MAX_LOG][MAX_N], Log[MAX_N];

inline bool Compare(const int& a, const int& b) {
    return Values[a] < Values[b];
}

inline int Query(const int left, const int right) {
    int step = Log[right - left + 1], length = 1 << Log[right - left + 1];
    if (Compare(RMQ[step][left], RMQ[step][right - length + 1]))
        return RMQ[step][left];
    else
        return RMQ[step][right - length + 1];
}

void BuildRMQ() {
    for (int i = 2; i <= N; ++i)
        Log[i] = Log[i / 2] + 1;
    for (int i = 1; i <= N; ++i)
        RMQ[0][i] = i;
    for (int step = 1, length = 2; length <= N; ++step, length <<= 1) {
        for (int i = 1; i + length - 1 <= N; ++i) {
            if (Compare(RMQ[step - 1][i], RMQ[step - 1][i + length / 2]))
                RMQ[step][i] = RMQ[step - 1][i];
            else
                RMQ[step][i] = RMQ[step - 1][i + length / 2];
        }
    }
}

int main() {
    ifstream in("rmq.in");
    ofstream out("rmq.out");
    int Q; in >> N >> Q;
    for (int i = 1; i <= N; ++i)
        in >> Values[i];
    BuildRMQ();
    for (; Q > 0; --Q) {
        int left, right; in >> left >> right;
        out << Values[Query(left, right)] << "\n";
    }
    in.close();
    out.close();
    return 0;
}