栈和队列典型习题总结

1.用队列实现栈

例子: 12 23 34 45 56 67 78

思路分析:需要有两个队列实现,栈是先进后出,后进先出。
入队列时:①两个队列都是空的,入qu1 ②有一个队列不是空的,入队列入非空队列。
出队列时:哪个不为空出哪个队列。出n-1到另一个队列,再把最后一个元素出栈。

import java.util.LinkedList;
import java.util.Queue;

/**
 * 两个队列实现栈
 */

public class MyStack {

    Queue<Integer> queue1 = new LinkedList<>();
    Queue<Integer> queue2 = new LinkedList<>();
    /** Initialize your data structure here. */
    public MyStack() {
    }

    /** Push element x onto stack. */
    //哪个栈不为空入哪个栈
    public void push(int x) {
        if (!queue1.isEmpty()) {
            queue1.offer(x);
        } else if (!queue2.isEmpty()) {
            queue2.offer(x);
        } else {
            queue1.offer(x);
        }
    }

    /** Removes the element on top of the stack and returns that element. */
    public int pop() {
        if (!queue1.isEmpty()) {
            int size1 = queue1.size()-1; //由于每次queue1.poll()导致size发生变化,因此要事先保存
            for (int i = 0; i < size1; i++) {
                queue2.offer(queue1.poll());
            }
            return queue1.poll();
        }
        if (!queue2.isEmpty()) {
            int size2 =  queue2.size()-1;
            for (int i = 0; i < size2; i++) {
                queue1.offer(queue2.poll());
            }
            return queue2.poll();
        }
        return -1;
    }

    /** Get the top element. */
    public int top() {
        if (!queue1.isEmpty()) {
            int size1 = queue1.size(); //由于每次queue1.poll()导致size发生变化,因此要事先保存
            int tmp = 0;  //查看栈顶元素,但是要把元素全部弹入另外一个栈,因为入栈的是非空栈
            for (int i = 0; i < size1; i++) {
                tmp = queue1.poll();
                queue2.offer(queue1.poll());
            }
            return tmp;
        }
        if (!queue2.isEmpty()) {
            int size2 =  queue2.size();
            int tmp = 0;
            for (int i = 0; i < size2; i++) {
                tmp = queue2.poll();
                queue1.offer(queue2.poll());
            }
            return tmp;
        }
        return -1;
    }

    /** Returns whether the stack is empty. */
    public boolean empty() {
        if (queue1.isEmpty() && queue2.isEmpty()) {
            return true;
        }
        return false;
    }
}

2.用栈实现队列

例子: 12 23 34 45 56 67 78

思路分析:需要用两个栈实现队列【第一个栈,入队;第二个栈,出队】
入栈:①入到stack1
出栈:要出stack1,把全部元素入到stack2,再把stack2的栈顶元素出出去。

import java.util.Stack;

class MyQueue {
    public Stack<Integer> stack1;
    public Stack<Integer> stack2;
    /** Initialize your data structure here. */
    public MyQueue() {
        stack1 = new Stack<>();
        stack2 = new Stack<>();
    }

    /** Push element x to the back of queue. */
    public void push(int x) {
        stack1.push(x);
    }

    /** Removes the element from in front of queue and returns that element. */
    public int pop() {
        if (stack2.isEmpty()) {
            while (!stack1.isEmpty()) {
                stack2.push(stack1.pop());
            }
        }
        if (!stack2.isEmpty()) {  //stack1可能为空
            return stack2.pop();
        }
        return -1;
    }

    /** Get the front element. */
    public int peek() {
        if (stack2.isEmpty()) {
            while (!stack1.isEmpty()) {
                stack2.push(stack1.pop());
            }
        }
        if (!stack2.isEmpty()) {  //stack1可能为空
            return stack2.peek();
        }
        return -1;
    }

    /** Returns whether the queue is empty. */
    public boolean empty() {
        return stack1.isEmpty() && stack2.isEmpty();
    }
}

3.括号匹配问题

"()" "(]" "{[]}" "()[]{}" "([)]" ")))))))))" "(((((((((((("

思路分析:要有一个栈,i遍历字符串,如果是左括号,入栈;如果是右括号,看栈顶元素是否匹配。

    public  static boolean isValid(String s) {
        Stack<Character> stack = new Stack<>();

        for (int i = 0; i < s.length(); i++) {
            char ch = s.charAt(i);
            if(ch == '(' || ch == '{'|| ch == '[') {
                stack.push(ch);
            }else {
                if(stack.empty()) {
                    System.out.println("右括号多");
                    return false;
                }
                char top = stack.peek();
                if(top == '(' && ch == ')' ||
                        top == '{' && ch == '}'||
                        top == '[' && ch == ']' ){
                    stack.pop();
                }else {
                    System.out.println("右括号匹配错误!");
                    return false;
                }
            }
        }

        if(!stack.empty()) {
            System.out.println("左括号多!");
            return false;
        }
        return true;
    }

4.实现一个最小栈

例子: 4 1 -3 8 2 从栈里面取元素,每次都是去的当前栈内最小的。

思路分析:需要两个栈 stack1 minstack ,并且minstack里面放的元素都是当前栈内最小的元素。
入栈时,先入stack1。minstack如果为空,入栈;如果不为空,要保证栈顶元素是当前栈内最小的元素,如果要入栈的元素比栈顶元素大,不入栈。
出栈时,若stack1和minstack栈顶元素相同,则同时出栈;否则只出stack1栈中的元素。

class MinStack {
        /** initialize your data structure here. */
    public Stack<Integer> stack = new Stack<>();
    public Stack<Integer> MinStack = new Stack<>();

    MinStack() {

    }
    
    void push(int x) {
        stack.push(x);
        if(MinStack.empty()) {
            MinStack.push(x);
        } else {
            int tmp = MinStack.peek();
            if(tmp >= x) {
                MinStack.push(x);
            }
        }
    }
    
    void pop() {
        int tmp = stack.pop();
        if(tmp == MinStack.peek()) {
            MinStack.pop();
        }
    }
    
    int top() {
        return stack.peek();
    }
    
    int getMin() {
        return MinStack.peek();
    }
}
发布了51 篇原创文章 · 获赞 14 · 访问量 2309

猜你喜欢

转载自blog.csdn.net/qq_41185460/article/details/103563818
今日推荐