Cod sursa(job #548936)

Utilizator cosmyoPaunel Cosmin cosmyo Data 7 martie 2011 22:46:37
Problema Struti Scor 40
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.14 kb
#include <cstdio>
using namespace std;
const int N = 1005;
const int INF = 1000000;
int a[N][N], mn[N][N], mx[N][N], dx, dy, dmin[N], dmax[N], p, n, m, MAX;

long long solve(int dx, int dy) {
	int i, j, front = 1, back = 0, p = 1, u = 0;
	long long nr = 0;
	for(i = 1; i <= n; ++i)
		for(j = 1; j <= m; ++j)
			mn[i][j] = mx[i][j] = 0;

	for(i = 1; i <= n; ++i) {
		front = 1; back = 0; p = 1; u = 0;

		for(j = 1; j <= m; ++j) {
			while(front <= back && a[i][dmin[back]] >= a[i][j])
				--back;
			dmin[++back] = j;

			while(p <= u && a[i][dmax[u]] <= a[i][j])
				--u;
			dmax[++u] = j;

			if(j >= dy){
				mn[i][j - dy + 1] = a[i][dmin[front]];
				mx[i][j - dy + 1] = a[i][dmax[p]];
			}

			if(dmin[back] - dmin[front] + 1 == dy)
				++front;

			if(dmax[u] - dmax[p] + 1 == dy)
				++p;
		}
	}
	/*	
	for(i = 1; i <= n; ++i) {
		for(j = 1; j <= m - dy + 1; ++j)
			printf("%d ", mn[i][j]);
		printf("\n");
	}
	printf("\n");
	for(i = 1; i <= n; ++i) {
		for(j = 1; j <= m - dy + 1; ++j)
			printf("%d ", mx[i][j]);
		printf("\n");
	}
	*/
	for(j = 1; j <= m - dy + 1; ++j) {
		front  = 1; back = 0; p = 1; u = 0;
		for(i = 1; i <= n; ++i) {
			while(front <= back && mn[i][j] <= mn[dmin[back]][j])
				--back;
			dmin[++back] = i;

			while(p <= u && mx[i][j] >= mx[dmax[u]][j])
				--u;
			dmax[++u] = i;
			
		//	printf("%d %d\n", mn[dmin[front]][j], mx[dmax[p]][j]);
			if(i >= dx) {
				if(mx[dmax[p]][j] - mn[dmin[front]][j] < MAX) {
					MAX = mx[dmax[p]][j] - mn[dmin[front]][j];
					nr = 0;
				}
				
				if(mx[dmax[p]][j] - mn[dmin[front]][j] == MAX)
					 ++nr;
			}

			if(dmin[back] - dmin[front] + 1 == dx)
				++front;

			if(dmax[u] - dmax[p] + 1 == dx)
				++p;
		}
	//	printf("\n");
	}
//	printf("%d\n", nr);
	return nr;
}

int main() {
	freopen("struti.in", "r", stdin);
	freopen("struti.out", "w", stdout);
	scanf("%d %d %d", &n, &m, &p);
	int i, j;
	long long nr = 0;
	for(i = 1; i <= n; ++i)
		for(j = 1; j <= m; ++j)
			scanf("%d", &a[i][j]);

	for(i = 1; i <= p; ++i) {
		scanf("%d %d", &dx, &dy);
		MAX = INF;
		nr = 0;
		nr +=(long long) solve(dx, dy);

		if(dx != dy) 
			nr +=(long long) solve(dy, dx);

		printf("%d %lld\n", MAX, nr);
	}

	return 0;
}