Cod sursa(job #603225)

Utilizator claudiumihailClaudiu Mihail claudiumihail Data 15 iulie 2011 02:49:33
Problema Range minimum query Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 1.67 kb
#include <fstream>
#include <iostream>
#include <cmath>

using namespace std;

#define MAXN 100000

typedef unsigned int uint32;

int computeLog2(const uint32 num)
{
	uint32 i;

	for (i=0; 1<<i <= num; ++i) ;
	
	return i-1;
}

void preprocess(int **mat, const int *a, const uint32 size)
{	
	for (uint32 i=0; i<size; ++i)
	{
		mat[i][0] = a[i];
	}
	
	for (uint32 j=1; (1<<j) < size; ++j)
	{
		for (uint32 i=0; i+(1<<j)-1 < size; ++i)
		{
			if (mat[i][j-1] <= mat[i+(1<<(j-1))][j-1])
				mat[i][j] = mat[i][j-1];
			else
				mat[i][j] = mat[i+(1<<(j-1))][j-1];
		}
	}
}

int query(int **mat, const uint32 i, const uint32 j)
{
	const uint32 l2 = j-i>0 ? computeLog2(j-i) : 0;
	
	//cout << "l2=" << l2 << endl;
	
	//cout << mat[i][l2] << " " << mat[j-(1<<l2)+1][l2] << endl;
	
	if (mat[i][l2] <= mat[j-(1<<l2)+1][l2])
		return mat[i][l2];
	
	return mat[j-(1<<l2)+1][l2];
}

int main()
{
	int n, m;
	int **mat, *a;
	fstream fin("rmq.in", fstream::in);
	fstream fout("rmq.out", fstream::out);
	
	a = new int[MAXN];

	mat = new int*[MAXN];
	for (uint32 i=0; i<MAXN; ++i)
	{
		mat[i] = new int[(int)log2(MAXN)+1];
	}
	
	fin >> n >> m;
	//cout << n << " " << m << endl;
	
	for (uint32 i=0; i<n; ++i)
	{
		fin >> a[i];
		//cout << a[i] << " ";
	}
	
	//cout << endl;
	
	preprocess(mat, a, n);
	
	/*for (int i=0; i<n; ++i)
	{
		cout << "mat[" << i << "]= ";
		for (int j=0; j<=(uint32)log2(n); ++j)
		{
			cout << mat[i][j] << " ";
		}
		cout << endl;
	}*/
	
	for (uint32 i=0; i<m; ++i)
	{
		uint32 x, y;
		
		fin >> x >> y;
		fout << query(mat, x-1, y-1) << "\n";
	}
	
	fin.close();
	fout.close();
	
	return 0;
}