今天来盘一盘 **栈以及队列 ** 这两类题目
使用python刷题分类整理的笔记,请参考: https://github.com/lxztju/leetcode-algorithm/tree/v1
栈: 先进先出
队列: 先进后出
利用这两类数据结构的特性解题.
其中一类非常经典的题目是: 单调栈(leetcode496题, 经典题目).
题解: 两个栈实现
示例
先入队[1,2], 然后执行一次出队, 再入队[3,4], 然后执行两次出队
class MyQueue {
public:
stack stackin;
stack stackout;
/** Initialize your data structure here. */
MyQueue() {
}
/** Push element x to the back of queue. */
void push(int x) {
stackin.push(x);
}
/** Removes the element from in front of queue and returns that element. */
int pop() {
// 如果stackout为空,将stackin中的元素依次放入stackout
if(stackout.empty())
while (!stackin.empty() ){
int tmp = stackin.top();
stackin.pop();
stackout.push(tmp);
}
// 返回stackout的栈顶元素
int tmp = stackout.top();
stackout.pop();
return tmp;
}
/** Get the front element. */
int peek() {
// 如果stackout为空,将stackin中的元素依次放入stackout
if(stackout.empty())
while (!stackin.empty() ){
int tmp = stackin.top();
stackin.pop();
stackout.push(tmp);
}
// 返回stackout的栈顶元素
return stackout.top();
}
/** Returns whether the queue is empty. */
bool empty() {
if (stackin.empty() && stackout.empty())
return true;
else
return false;
}
};
题解: 两个队列实现
q1存储栈中的元素, q2作为入栈时的辅助栈
入栈时,先将元素入队到q2, 然后将q1中的元素出队并放入q2中, 此时q2队首的元素即为栈顶元素, 将q1与q2互换, q2始终作为辅助栈.
class MyStack {
public:
/** Initialize your data structure here. */
queue q1;
queue q2;
MyStack() {
}
/** Push element x onto stack. */
void push(int x) {
q2.push(x);
while(!q1.empty()){
q2.push(q1.front());
q1.pop();
}
swap(q1, q2);
}
/** Removes the element on top of the stack and returns that element. */
int pop() {
int tmp = q1.front();
q1.pop();
return tmp;
}
/** Get the top element. */
int top() {
return q1.front();
}
/** Returns whether the stack is empty. */
bool empty() {
return q1.empty();
}
};
class MinStack {
public:
stack s1;
stack s2; // 辅助栈
/** initialize your data structure here. */
MinStack() {
}
void push(int x) {
s1.push(x);
if (s2.empty())
s2.push(x);
else{
int tmp = s2.top();
if (x <= tmp)
s2.push(x);
else
s2.push(tmp);
}
}
void pop() {
s1.pop();
s2.pop();
}
int top() {
return s1.top();
}
int getMin() {
return s2.top();
}
};
class Solution {
public:
bool isValid(string s) {
unordered_map parentheses = {
{'(', ')'}, {'[', ']'}, {'{', '}'}}; // 字典
stack stack1;
for (auto s1: s){
// s1为右括号
if (parentheses.find(s1) == parentheses.end()){
// 如果栈为空, 返回false
if (stack1.empty()) return false;
else{
char tmp = stack1.top();
stack1.pop();
// 如果栈顶元素与s1不对应, 返回false
if (parentheses[tmp] != s1) return false;
}
}
// s1为左括号, 入栈
else{
stack1.push(s1);
}
}
//最后栈为空返回true, 否则返回false.
if (!stack1.empty()) return false;
else return true;
}
};
class Solution {
public:
string removeOuterParentheses(string S) {
string res;
stack stack1;
for (auto s1: S){
if (s1 == '('){
stack1.push(s1);
if (stack1.size() > 1)
res += s1;
}
else{
stack1.pop();
if (stack1.size() >= 1)
res += ')';
}
}
return res;
}
};
class Solution {
public:
vector nextGreaterElement(vector& nums1, vector& nums2) {
vector res;
unordered_map nums2Index;
for (int i = 0; i< nums2.size(); i++){
nums2Index.insert(make_pair(nums2[i], i));
}
// 暴力法
for(int i = 0; i< nums1.size(); i++){
bool flag = true;
for (int j = nums2Index[nums1[i]]; j< nums2.size(); j++){
if (nums2[j] > nums1[i]){
res.push_back(nums2[j]);
flag = false;
break;
}
}
if (flag) res.push_back(-1);
}
return res;
}
};
class Solution {
public:
vector nextGreaterElement(vector& nums1, vector& nums2) {
vector res;
unordered_map nums2Index;
// 单调栈
stack decendStack;
for (int i = 0; i < nums2.size(); i++){
if (decendStack.empty() || decendStack.top() >= nums2[i])
decendStack.push(nums2[i]);
else{
while (!decendStack.empty() && decendStack.top() < nums2[i]){
nums2Index[decendStack.top()] = nums2[i];
decendStack.pop();
}
decendStack.push(nums2[i]);
}
}
// 最终如果栈非空, 那么栈中下一个最大的元素不存在
while (! decendStack.empty()){
int tmp = decendStack.top();
decendStack.pop();
nums2Index[tmp] = -1;
}
for(int i = 0; i< nums1.size(); i++){
res.push_back(nums2Index[nums1[i]]);
}
return res;
}
};
class Solution {
public:
vector nextGreaterElements(vector& nums) {
stack stk;
vector res(nums.size(), -1);
for(int i = 0; i < nums.size() * 2; i++)
{
int index = i % nums.size();
while(!stk.empty() && nums[stk.top()] < nums[index])
{
// 如果已经找到了下一个最大的元素, 那么跳过
if(res[stk.top()] == -1)
{
res[stk.top()] = nums[index];
}
stk.pop();
}
stk.push(index);
}
return res;
}
};
class Solution {
public:
vector dailyTemperatures(vector& T) {
vector res(T.size(), 0);
stack stk;
// 遍历T
for (int i = 0; i< T.size(); i++){
// 如果新的气温大于栈顶的气温, 那么保存需要等待的天数(索引值差)
// 栈顶出栈
while(!stk.empty() && T[stk.top()] < T[i]){
res[stk.top()] = i - stk.top();
stk.pop();
}
stk.push(i);
}
return res;
}
};
微信公众号: 小哲AI
GitHub地址: https://github.com/lxztju/leetcode-algorithm
csdn博客: https://blog.csdn.net/lxztju
知乎专栏: 小哲AI
AI研习社专栏:小哲AI