栈与队列的常见应用算法及Java实现

一、栈的常见应用算法

1.1 括号匹配

java 复制代码
import java.util.Stack;

public class BracketMatcher {
    public static boolean isValid(String s) {
        Stack<Character> stack = new Stack<>();
        for (char c : s.toCharArray()) {
            if (c == '(' || c == '[' || c == '{') {
                stack.push(c);
            } else {
                if (stack.isEmpty()) return false;
                char top = stack.pop();
                if ((c == ')' && top != '(') || 
                    (c == ']' && top != '[') || 
                    (c == '}' && top != '{')) {
                    return false;
                }
            }
        }
        return stack.isEmpty();
    }

    public static void main(String[] args) {
        System.out.println(isValid("()[]{}")); // true
        System.out.println(isValid("([)]"));   // false
    }
}

1.2 逆波兰表达式求值

java 复制代码
import java.util.Stack;

public class ReversePolishNotation {
    public static int evalRPN(String[] tokens) {
        Stack<Integer> stack = new Stack<>();
        for (String token : tokens) {
            if (token.equals("+")) {
                stack.push(stack.pop() + stack.pop());
            } else if (token.equals("-")) {
                int b = stack.pop();
                int a = stack.pop();
                stack.push(a - b);
            } else if (token.equals("*")) {
                stack.push(stack.pop() * stack.pop());
            } else if (token.equals("/")) {
                int b = stack.pop();
                int a = stack.pop();
                stack.push(a / b);
            } else {
                stack.push(Integer.parseInt(token));
            }
        }
        return stack.pop();
    }

    public static void main(String[] args) {
        String[] tokens = {"2", "1", "+", "3", "*"};
        System.out.println(evalRPN(tokens)); // 9
    }
}

1.3 深度优先搜索(DFS)

java 复制代码
void dfs(Node start) {
    Deque<Node> stack = new ArrayDeque<>();
    Set<Node> visited = new HashSet<>();
    
    stack.push(start);
    visited.add(start);
    
    while (!stack.isEmpty()) {
        Node current = stack.pop();
        System.out.println(current.value); // 处理当前节点
        
        // 将当前节点的未访问过的邻居压入栈
        for (Node neighbor : current.neighbors) {
            if (!visited.contains(neighbor)) {
                stack.push(neighbor);
                visited.add(neighbor);
            }
        }
    }
}

二、队列的常见应用算法

2.1 滑动窗口最大值(双端队列)

java 复制代码
import java.util.*;

public class SlidingWindowMaximum {
    public int[] maxSlidingWindow(int[] nums, int k) {
        if (nums == null || k <= 0) return new int[0];
        
        int n = nums.length;
        int[] result = new int[n - k + 1];
        int ri = 0;
        
        Deque<Integer> deque = new ArrayDeque<>();
        for (int i = 0; i < n; i++) {
            // 移除超出窗口范围的元素
            while (!deque.isEmpty() && deque.peek() < i - k + 1) {
                deque.poll();
            }
            
            // 移除所有小于当前元素的元素,保持队列递减
            while (!deque.isEmpty() && nums[deque.peekLast()] < nums[i]) {
                deque.pollLast();
            }
            
            deque.offer(i);
            
            // 记录窗口最大值
            if (i >= k - 1) {
                result[ri++] = nums[deque.peek()];
            }
        }
        
        return result;
    }
    
    public static void main(String[] args) {
        SlidingWindowMaximum solution = new SlidingWindowMaximum();
        int[] nums = {1, 3, -1, -3, 5, 3, 6, 7};
        int k = 3;
        int[] result = solution.maxSlidingWindow(nums, k);
        System.out.println(Arrays.toString(result)); // [3, 3, 5, 5, 6, 7]
    }
}

2.2 寻找第K大元素(优先队列/堆)

java 复制代码
import java.util.PriorityQueue;

public class KthLargestElement {
    public int findKthLargest(int[] nums, int k) {
        PriorityQueue<Integer> minHeap = new PriorityQueue<>();
        
        for (int num : nums) {
            minHeap.offer(num);
            if (minHeap.size() > k) {
                minHeap.poll();
            }
        }
        
        return minHeap.peek();
    }
    
    public static void main(String[] args) {
        KthLargestElement solution = new KthLargestElement();
        int[] nums = {3, 2, 1, 5, 6, 4};
        int k = 2;
        System.out.println(solution.findKthLargest(nums, k)); // 5
    }
}

2.3 广度优先搜索(BFS)

java 复制代码
public void bfs(Node start) {
    if (start == null) {
        return;
    }
    
    Queue<Node> queue = new LinkedList<>();
    Set<Node> visited = new HashSet<>();
    
    queue.offer(start);
    visited.add(start);
    
    while (!queue.isEmpty()) {
        Node current = queue.poll();
        System.out.print(current.val + " ");
        
        // 处理当前节点的邻居
        for (Node neighbor : current.neighbors) {
            if (!visited.contains(neighbor)) {
                visited.add(neighbor);
                queue.offer(neighbor);
            }
        }
    }
}
相关推荐
熙客3 分钟前
Java:LinkedList的使用
java·开发语言
CYRUS_STUDIO10 分钟前
Miniconda 全攻略:优雅管理你的 Python 环境
前端·后端·python
浩少70217 分钟前
LeetCode-22day:多维动态规划
算法·leetcode·动态规划
blueblood19 分钟前
🗄️ JFinal 项目在 IntelliJ IDEA 中的 Modules 配置指南
java·后端
●VON24 分钟前
如何通过docker进行本地部署?
java·docker·容器
杨杨杨大侠1 小时前
第8篇:Spring Boot集成 - 开发自己的Starter
java·spring·开源
岁月静好20251 小时前
Leetcode 深度优先搜索 (15)
算法·leetcode·深度优先
合作小小程序员小小店1 小时前
挖漏洞三步走
python·网络协议·web安全·网络安全·安全威胁分析
赵得C1 小时前
Java 多线程环境下的全局变量缓存实践指南
java·开发语言·后端·spring·缓存
离越词1 小时前
C++day1作业
数据结构·c++·算法