http://poj.org/problem?id=2823

裸的单调队列.

注意: 队列里存的是下标, 就不要把他当做值用- -

代码:

#include<cstdio>
#include<cstring>
#include<iostream>
#include<cmath>
#include<string>
#include<vector>
#include<map>
#include<algorithm>
using namespace std;
inline int Rint() { int x; scanf("%d", &x); return x; }
inline int max(int x, int y) { return (x>y)? x: y; }
inline int min(int x, int y) { return (x<y)? x: y; }
#define FOR(i, a, b) for(int i=(a); i<=(b); i++)
#define FORD(i,a,b) for(int i=(a);i>=(b);i--)
#define REP(x) for(int i=0; i<(x); i++)
typedef long long int64;
#define INF (1<<30)
const double eps = 1e-8;
#define bug(s) cout<<#s<<"="<<s<<" "

//	裸的单调队列. 
//	d[i] = min{ a[j] | j=[i-K+1, i], j>=0 }

#define MAXN 1000002
int q[MAXN];		//min
int f[MAXN];
int front, tail;

int q2[MAXN];		//max
int front2, tail2;

int minx[MAXN];
int maxx[MAXN];

int main()
{
	int n = Rint();
	int K= Rint();
	front = tail  = 0;
	front2 = tail2 = 0;
	FOR(i, 1, n)		//online
	{
		f[i] = Rint();
		//	把  i 丢进队列
		while(front<tail && f[q[tail-1]]>f[i]) tail--;
		q[tail++] = i;
		while(front2<tail2 && f[q2[tail2-1]]<f[i]) tail2--;
		q2[tail2++] = i;

		//bug(q[front]);bug(f[q[front]])<<endl;
		if(i>=K)	//	取front 作为 最值
		{
			int low = i-K+1;
			while(q[front]<low) front++;
			minx[i] = f[q[front]];
			while(q2[front2]<low) front2++;
			maxx[i] = f[q2[front2]];
		}
	}
	FOR(i, K, n)
	{
		printf("%d", minx[i]);
		if(i!=n) putchar(' ');
	}
	putchar('\n');
	FOR(i, K, n)
	{
		printf("%d", maxx[i]);
		if(i!=n) putchar(' ');
	}	
	putchar('\n');
}