题目描述
给定一个只包括 '(',')','{','}','[',']' 的字符串,判断字符串是否有效。
有效字符串需满足:左括号必须用相同类型的右括号闭合。左括号必须以正确的顺序闭合。
说明:注意空字符串可被认为是有效字符串。
示例 1:
输入: "()"
输出: true
示例 2:
输入: "()[]{}"
输出: true
示例 3:
输入: "(]"
输出: false
示例 4:
输入: "([)]"
输出: false
示例 5:
输入: "{[]}"
输出: true
分析:1、在遍历字符串的过程中,遇到 左括号 就让它入栈,遇到 右括号 就判断下栈里面有没有 左括号:
(1)如果有,则把处于栈顶的 左括号 弹出,相当于和 右括号 进行匹配,然后继续往后遍历字符串。
(2)如果没有,则匹配失败。相当于字符串的最前面出现了 右括号 ,显然这是不合理的。
2、当字符串遍历完成,判断栈是否为空,如果为空则表示字符串有效,否则无效。
性能优化:先判定字符串长度是否为偶数,提高速度; if (s.length() % 2 != 0) return false;
class Solution {
public boolean isValid(String s) {
if (s == null || s.length() == 0)
return true;
//先判定字符串长度是否为偶数,提高速度
if (s.length() % 2 != 0)
return false;
Stack<Character> stack = new Stack<>();
for (char c : s.toCharArray()) {
if (c == '(')
stack.push(')');
else if (c == '[')
stack.push(']');
else if (c == '{')
stack.push('}');
else if (stack.empty() || c != stack.pop())
return false;
}
if (stack.empty())
return true;
return false;
}
}
面试例题(字节跳动):
给定一个只包括 '(',')'的字符串,判断字符串是否有效。注:空字符串属于有效字符串。
示例 1:
输入: "(())"
输出: true
示例 2:
输入: "())("
输出: false
public class Solution {
public static boolean isValid2(String s) {
if (s == null || s.length() == 0)
return true;
//先判定字符串长度是否为偶数,提高速度
if (s.length() % 2 != 0)
return false;
Stack<Character> stack = new Stack<>();
for (int i = 0; i < s.length(); i++) {
if (s.charAt(i) == '(')
stack.push('(');
else {
if (stack.isEmpty())
return false;
else
stack.pop();
}
}
if (stack.isEmpty())
return true;
return false;
}
}
性能优化:栈里存放的是同一种字符"(" ,可以用一个变量来取代栈,该变量记录 "(" 的个数,遇到 "(" 变量加 1,遇到 ")" 变量减 1,栈为空就相当于变量的值为 0。时间复杂度为 O(n),空间复杂度 O(n) -->O(1)
public class Solution {
public static boolean isValid3(String s) {
if (s == null || s.length() == 0)
return true;
//先判定字符串长度是否为偶数,提高速度
if (s.length() % 2 != 0)
return false;
// 用来记录遇到的 "(" 的个数
int sum = 0;
for (int i = 0; i < s.length(); i++) {
if (s.charAt(i) == '(')
sum++;
else {
if (sum == 0)
return false;
else
sum--;
}
}
return sum == 0 ? true : false;
}
}