算法训练day11|20. 有效的括号;1047. 删除字符串中的所有相邻重复项;150. 逆波兰表达式求值

简介: 算法训练day11|20. 有效的括号;1047. 删除字符串中的所有相邻重复项;150. 逆波兰表达式求值

LeetCode:20. 有效的括号

有效的括号-力扣(leetcode)

1.思路

题意:括号是对称排列的!!栈和(双端)队列都可以解决。

#双端队列既可以当作栈,又可以当作队列使用.

思路:

①定义栈:存储左括号对应的右括号;

②判断是否相等,不满足条件的有三种情况:左括号多了、右括号多了、括号不匹配;其中括号不匹配和"左括号多了"可以默认同一种情况。


2.代码实现

  1// 双端队列调用栈方法实现
  2class Solution {
  3    public boolean isValid(String s) {
  4        Deque<Character> deque = new LinkedList<>();
  5
  6        for (int i = 0; i < s.length(); i++) {
  7            // 左侧括号处理操作,直接加入
  8            if (s.charAt(i) == '(') {
  9                deque.push(')');
 10            } else if (s.charAt(i) == '{') {
 11                deque.push('}');
 12            } else if (s.charAt(i) == '[') {
 13                deque.push(']');
 14
 15            // 右括号处理操作;
 16            // 不匹配:右括号多了;左括号多了和括号不匹配;
 17            } else if (deque.isEmpty() || deque.peek() != s.charAt(i)) {
 18                return false;
 19            } else {
 20            // 匹配:直接弹出
 21                deque.pop(); 
 22            }
 23        } 
 24        // 判断是否为空?true : false;
 25        return deque.isEmpty();
 26    }
 27}
 28// 双端队列调用队列方法实现
 29class Solution {
 30    public boolean isValid(String s) {
 31        Deque<Character> deque = new LinkedList<>();
 32
 33        for (int i = 0; i < s.length(); i++) {
 34            // 左侧括号处理操作,直接加入
 35            if (s.charAt(i) == '(') {
 36                deque.offer(')');
 37            } else if (s.charAt(i) == '{') {
 38                deque.offer('}');
 39            } else if (s.charAt(i) == '[') {
 40                deque.offer(']');
 41
 42            // 右括号处理操作;
 43            // 不匹配:右括号多了;左括号多了和括号不匹配;
 44            } else if (deque.isEmpty() || deque.peek() != s.charAt(i)) {
 45                return false;
 46            } else {
 47            // 匹配:直接弹出
 48                deque.poll(); 
 49            }
 50        } 
 51        // 判断是否为空?true : false;
 52        return deque.isEmpty();
 53    }
 54}
 55// 用队列实现
 56class Solution {
 57    public boolean isValid(String s) {
 58        Queue<Character> queue = new LinkedList<>();
 59
 60        for (int i = 0; i < s.length(); i++) {
 61            // 左侧括号处理操作,直接加入
 62            if (s.charAt(i) == '(') {
 63                queue.offer(')');
 64            } else if (s.charAt(i) == '{') {
 65                queue.offer('}');
 66            } else if (s.charAt(i) == '[') {
 67                queue.offer(']');
 68
 69            // 右括号处理操作;
 70            // 不匹配:右括号多了;左括号多了和括号不匹配;
 71            } else if (queue.isEmpty() || queue.peek() != s.charAt(i)) {
 72                return false;
 73            } else {
 74            // 匹配:直接弹出
 75                queue.poll(); 
 76            }
 77        } 
 78        // 判断是否为空?true : false;
 79        return queue.isEmpty();
 80    }
 81}
 82
 83// 用栈实现
 84class Solution {
 85    public boolean isValid(String s) {
 86        Stack<Character> stack = new Stack<>();
 87
 88        for (int i = 0; i < s.length(); i++) {
 89            // 左侧括号处理操作,直接加入
 90            if (s.charAt(i) == '(') {
 91                stack.push(')');
 92            } else if (s.charAt(i) == '{') {
 93                stack.push('}');
 94            } else if (s.charAt(i) == '[') {
 95                stack.push(']');
 96
 97            // 右括号处理操作;
 98            // 不匹配:右括号多了;左括号多了和括号不匹配;
 99            } else if (stack.isEmpty() || stack.peek() != s.charAt(i)) {
100                return false;
101            } else {
102            // 匹配:直接弹出
103                stack.pop(); 
104            }
105        } 
106        // 判断是否为空?true : false;
107        return stack.isEmpty();
108    }
109}


3.复杂度分析

时间复杂度: for循环下的时间复杂度是O(n)

空间复杂度: 创建栈或队列空间为n,则空间复杂度O(n)


LeetCode:1047. 删除字符串中的所有相邻重复项

1047. 删除字符串中的所有相邻重复项 - 力扣(LeetCode)


1.思路

该题和(20. 有效的括号)思路一致,可以将逻辑模板化;

遍历进行入栈、出栈的操作,判断栈是否为空,不为空则输出字符串,最后需要进行反转一下。

2.代码实现
 1// 用栈实现(当然可以使用(双端)队列调用相应方法来实现)
 2class Solution {
 3    public String removeDuplicates(String s) {
 4        Stack<Character> stack = new Stack<>();
 5        char ch;
 6        // 判断是否相等,进行入栈和出栈的操作
 7        for (int i = 0; i < s.length(); i++) {
 8            ch = s.charAt(i);
 9            if (stack.isEmpty() || stack.peek() != ch) {
10                stack.push(ch);
11            } else {
12                stack.pop();
13            }
14        }
15        String str = "";
16        while (!stack.isEmpty()) {
17            str += stack.pop();
18        }
19        return new StringBuffer(str).reverse().toString();
20     }
21}
3.复杂度分析

时间复杂度:for循环遍历时间复杂度为O(n);

空间复杂度:创建栈空间和str以及StringBuffer,则空间复杂度为3O(n);

4.参考
代码随想录(programmercarl.com)

LeetCode:150. 逆波兰表达式求值

150.逆波兰表达式求值-力扣(leetcode)

1.思路

逆波兰表达式求值是计算机实现计算的逻辑;

类似消除重复字符串的实现逻辑,整体遍历入栈:遇到"+ - * /"则进行操作计算,将结果入栈;遇到数子将对象入栈。最终返回栈内元素即可。

2.代码实现
 1class Solution {
 2    public int evalRPN(String[] tokens) {
 3        Stack<Integer> stack = new Stack<>();
 4        for (String s : tokens) { // 增强for循环,s表示为tokens[i]的内容
 5            if ("+".equals(s)) {
 6                stack.push(stack.pop() + stack.pop());
 7            } else if ("-".equals(s)) {
 8                stack.push(-stack.pop() + stack.pop()); // 先弹出的被减
 9            } else if ("/".equals(s)) {
10                int temp1 = stack.pop();
11                int temp2 = stack.pop();
12                stack.push(temp2/temp1); // 先弹出的被/
13            } else if ("*".equals(s)){
14                stack.push(stack.pop() * stack.pop());
15            } else {
16                stack.push(Integer.valueof(s)); // Integer.parseInt(s)
17            }
18        }
19        return stack.pop();
20    }
21}
3.复杂度分析

时间复杂度:O(n);一层for循环遍历

空间复杂度:O(n);创建栈空间

4.参考

代码随想录(programmercarl.com)

相关文章
|
2月前
|
算法
【优选算法】—— 字符串匹配算法
【优选算法】—— 字符串匹配算法
|
3月前
|
人工智能 算法 测试技术
【动态规划】【字符串】【C++算法】940. 不同的子序列 II
【动态规划】【字符串】【C++算法】940. 不同的子序列 II
|
4月前
|
算法 测试技术 C#
【动态规划】【字符串】C++算法:正则表达式匹配
【动态规划】【字符串】C++算法:正则表达式匹配
|
3月前
|
机器学习/深度学习 算法 C语言
【编码狂想】深度探索C++编程之旅:“数组、字符串、函数与KMP算法解密“
【编码狂想】深度探索C++编程之旅:“数组、字符串、函数与KMP算法解密“
73 0
|
11天前
|
算法
代码随想录算法训练营第五十五天 | LeetCode 583. 两个字符串的删除操作、72. 编辑距离、编辑距离总结
代码随想录算法训练营第五十五天 | LeetCode 583. 两个字符串的删除操作、72. 编辑距离、编辑距离总结
22 1
|
20天前
|
算法
【算法学习--字符串】(不含KMP算法)
【算法学习--字符串】(不含KMP算法)
|
2月前
|
算法 Java
[Java·算法·简单] LeetCode 28. 找出字符串中第一个匹配项的下标 详细解读
[Java·算法·简单] LeetCode 28. 找出字符串中第一个匹配项的下标 详细解读
23 0
|
2月前
|
算法 安全 Java
【数据结构与算法】6、栈(Stack)的实现、LeetCode:有效的括号
【数据结构与算法】6、栈(Stack)的实现、LeetCode:有效的括号
21 0
|
3月前
|
搜索推荐 算法
在冒泡排序算法中,为什么每次比较相邻的元素时都要进行交换?
【2月更文挑战第8天】【2月更文挑战第21篇】在冒泡排序算法中,为什么每次比较相邻的元素时都要进行交换?
|
3月前
|
算法 测试技术 C++
【字符串】【 LCP】【C++算法】2573找出对应 LCP 矩阵的字符串
【字符串】【 LCP】【C++算法】2573找出对应 LCP 矩阵的字符串