题目连接:
http://acm.hdu.edu.cn/showproblem.php?pid=1506
题目大意:
给出一个数列An,问以Ai为最小值的区间内有多少个元素?
解题思路:
手动模拟一个栈。栈内元素为一个单调不递减序列。当新元素Ai需要进栈,如果栈顶元素大于Ai,弹出栈顶元素,直到栈顶元素不大于Ai,Ai进栈。
这里可以保证i是高为栈顶元素的矩形向后延伸的边界,弹出过程中记录高为Ai的矩阵向前延伸的边界。
//#include <bits/stdc++.h>
#include <iostream>
#include <algorithm>
#include <cstdio>
using namespace std;
const int maxn = ;
#define LL long long//要用LL,数据范围太大,int会溢出
struct node
{
LL x, index;
} Stack[maxn]; int main ()
{
LL n;
while (scanf ("%I64d", &n), n)
{
LL sum = ;
LL head, last, num, m;
head = ;
last = -;
for (LL i=; i<=n; i++)
{
if (i == n)//在数列后面加一个0,以便于清空栈内元素
num = ;
else
scanf ("%I64d", &num);
m = i;//记录当前元素向前延伸的边界
while (head<=last && Stack[last].x>num)
{
sum = max(sum, (i - Stack[last].index)*Stack[last].x);
m = Stack[last].index;
last --;
}
Stack[++last].index = m;
Stack[last].x = num;
}
printf ("%I64d\n", sum);
}
return ;
}