Cod sursa(job #2300850)

Utilizator Anastasia11Susciuc Anastasia Anastasia11 Data 12 decembrie 2018 10:41:44
Problema Range minimum query Scor 40
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 1.39 kb
//sqrt solution
#include <iostream>
#include <fstream>
#include <cmath>
#define INF (1<<28)
#define Nmax 100005

using namespace std;

ifstream f("rmq.in");
ofstream g("rmq.out");

int n, q, rt, v[Nmax];
int sqr[Nmax];
int cnt=0, x, y;

void read()
{
    //f >> n >> q;
    scanf("%d%d", &n, &q);
    for (int i = 1; i <= n; i++)
    {
        //f >> v[i];
        scanf("%d", &v[i]);
        sqr[i] = INF;
    }
}

int findRoot(int n)
{
    int rt=0;
    while(rt*rt<=n) rt++;
    rt--;
    return rt;
}

void build()
{
    for (int i = 1; i <= n; i++)
    {
        int j = i;
        cnt++;
        for (; i <= min(j+rt-1, n); i++)
        {
            sqr[cnt]=min(sqr[cnt], v[i]);
        }
        i--;
    }
}

int query(int x, int y)
{
    int j=1, ans=INF;
    for (; rt*j < x; j++);
    int X=min(y, j*rt);
    j++;
    for (; j*rt <=y; j++)
        ans=min(ans, sqr[j]);
    int Y=max(rt*(j-1), x);

    for (int i = x; i <= X; i++) ans=min(ans, v[i]);
    for (int i = Y; i <= y; i++) ans=min(ans, v[i]);

    return ans;
}

int main()
{
    freopen("rmq.in", "r", stdin);
    freopen("rmq.out", "w", stdout);
    read();
    rt=findRoot(n);
    build();
    while(q--)
    {
        scanf("%d%d", &x, &y);
        //f >> x >> y;
        printf("%d\n", query(x, y));
        //g << query(x, y) << '\n';
    }
    return 0;
}