题目描述:
编写一个 StockSpanner 类,它收集某些股票的每日报价,并返回该股票当日价格的跨度。
今天股票价格的跨度被定义为股票价格小于或等于今天价格的最大连续日数(从今天开始往回数,包括今天)。
例如,如果未来7天股票的价格是 [100, 80, 60, 70, 60, 75, 85],那么股票跨度将是 [1, 1, 1, 2, 1, 4, 6]。
示例:
输入:[“StockSpanner”,“next”,“next”,“next”,“next”,“next”,“next”,“next”], [[],[100],[80],[60],[70],[60],[75],[85]]
输出:[null,1,1,1,2,1,4,6]
解释:
首先,初始化 S = StockSpanner(),然后:
S.next(100) 被调用并返回 1,
S.next(80) 被调用并返回 1,
S.next(60) 被调用并返回 1,
S.next(70) 被调用并返回 2,
S.next(60) 被调用并返回 1,
S.next(75) 被调用并返回 4,
S.next(85) 被调用并返回 6。
注意 (例如) S.next(75) 返回 4,因为截至今天的最后 4 个价格
(包括今天的价格 75) 小于或等于今天的价格。
思路:
题意即: 求出最近的一个大于今天价格的日子
- 得到一个新的价格 (price) .
- 取栈顶元素, 和 price 比一下, 如果他小于等于 price , 把它出栈并将他的的跨度记录下来
- 继续上一步的操作, 直到找到大于新的价格的元素, 用 tmp 累加计数跨度
- 最后将新的价格和他的跨度 tmp 入栈
代码实现:
class StockSpanner {
// 创建两个栈
Stack<Integer> prices = new Stack<>(); // 存放价格
Stack<Integer> span = new Stack<>(); // 存放跨度
public StockSpanner() {
}
public int next(int price) {
int tmp = 1; // 创建一个变量用来累加跨度
while (!prices.isEmpty() && prices.peek() <= price) {
prices.pop();
tmp += span.pop();
}
// 循环结束, 所有小于等于 price 的跨度都被累加起来了, 此时将 price 和它的跨度 tmp 入栈等待即可
prices.push(price);
span.push(tmp);
return tmp;
}
}