题目链接 : 点击查看
题目描述 :
给定一个长度为 N 的整数数列,输出每个数左边第一个比它小的数,如果不存在则输出 −1。
输入输出 :
输入
5
3 4 2 7 5
输出
-1 3 -1 2 2
题目分析 :
单调栈即为从栈底元素到栈顶元素单调递增或者是单调递减的栈。本题要求输出每个数左边第一个比它小的数,用单调栈处理时间复杂度较小,而且要维持一个单调递增的栈,储存比当前数小的元素,因为对于每个数如果这个数比栈顶元素小的话,那么栈顶元素就不再会成为之后的每一个数左边第一个比它小的数(仔细想一想),将栈顶元素出栈直到比当前数小,将当前数入栈(维持栈的单调递增)。如果当前数比栈顶元素大的话,就直接入栈,没有上述调整操作。在当前数入栈之前,栈顶元素就是每个数左边第一个比它小的数。详见如下代码。
代码 :
#include<iostream>
#include<cstdio>
using namespace std;
const int N = 100010;
int stk[N], top;
int main() {
int n;
cin >> n;
while (n -- ) {
int x;
scanf("%d", &x);
while (top && stk[top] >= x) top -- ;
if (!top) printf("-1 ");
else printf("%d ", stk[top]);
stk[ ++ top] = x;
}
return 0;
}
------------------------------------------------------------------------------
在此给出单调栈的相应模板
常见模型:找出每个数左边离它最近的比它大/小的数
int tt = 0;
for (int i = 1; i <= n; i ++ )
{
while (tt && check(stk[tt], i)) tt -- ;
stk[ ++ tt] = i;
}