题目
给定一个只包括 ‘(’,’)’,’{’,’}’,’[’,’]’ 的字符串,判断字符串是否有效。
有效字符串需满足:
左括号必须用相同类型的右括号闭合。
左括号必须以正确的顺序闭合。
注意空字符串可被认为是有效字符串。
示例 1:
输入: “()”
输出: true
示例 2:
输入: “()[]{}”
输出: true
示例 3:
输入: “(]”
输出: false
示例 4:
输入: “([)]”
输出: false
示例 5:
输入: “{[]}”
输出: true
分析
首先审题,字符串只包含开括号或者闭括号,判断括号是否有效。其实这道题很好想到采用栈来解决,遇到开括号入栈,闭括号取出栈顶的开括号比较与闭括号是否同一类型。如果是同一类型弹出栈顶的开括号,遍历完字符串后,如果栈为空,则证明字符串为有效字符串。
代码实现
/**
* 判断有效字符串 时间复杂度是O(n) 空间复杂度O(m)
* @param s
* @return
*/
private boolean isValid(String s){
if ("".equals(s)){
return true;
}
Stack<Character> stack = new Stack<>();
int length = s.length();
for (int i = 0; i < length; i++) {
if (s.charAt(i) == '(' || s.charAt(i) == '[' || s.charAt(i) == '{'){
// 左括号进栈
stack.push(s.charAt(i));
}else {
if (stack.empty()){
// 是右括号先出现
return false;
}else {
// 出现右括号
String str = stack.peek() +""+ s.charAt(i);
if (str.equals("()") || str.equals("{}") || str.equals("[]")){
stack.pop();
}else {
return false;
}
}
}
}
if (stack.empty()){
return true;
}
return false;
}
提交结果
性能分析
看着提交报告就应该知道这个方案的性能不是很好,分析下时间复杂度是O(n),n是字符串的长度,空间复杂度是O(m),m是最长有效字符串的长度的一半,其实从这个算法的复杂度上我觉得已经没有什么可以优化的了,但是代码确实有点冗余,比如判断闭括号的那段逻辑,我觉得无论是对时间复杂度还是空间复杂度都是有一定的影响的,所以优化如下的方案。
优化后的代码
/**
* 判断有效字符串 时间复杂度是O(n) 空间复杂度O(m)
* @param s
* @return
*/
private boolean isValid2(String s){
if ("".equals(s)){
return true;
}
Stack<Character> stack = new Stack<>();
int length = s.length();
for (int i = 0; i < length; i++) {
if (s.charAt(i) == '(' || s.charAt(i) == '[' || s.charAt(i) == '{'){
// 左括号进栈
stack.push(s.charAt(i));
}else {
if (stack.empty()){
// 是右括号先出现
return false;
}else {
// 出现右括号 判断栈顶元素与当前元素是否是同一类型的括号
if ((stack.peek() == '(' && s.charAt(i) == ')')
|| (stack.peek() == '[' && s.charAt(i) == ']')
|| (stack.peek() == '{' && s.charAt(i) == '}')){
stack.pop();
}else {
return false;
}
}
}
}
if (stack.empty()){
return true;
}
return false;
}
再次提交
性能分析
这次代码的执行用时和内存消耗都提升了一倍的性能,但是其实改的代码也就是闭括号逻辑判断的处理。
总结
这道题是一道很简单的题,但是考查的点其实是挺好的,是一个经典的栈的使用,上一篇算法的题里,我就提到了算法讲究的是思维方式的拓展,可以先窥探他人的思维方式,然后再培养自己的思维方式,最后想提的是,优化代码不仅仅是算法的改进,也可以是代码的优化,我们今天这道题两种方法的算法逻辑是一样的,但是优雅了代码的写法就提升了近一倍的性能,所以大家在写代码时还是要尽量优雅。
扫码关注公众号
来源:CSDN
作者:yutian_1999
链接:https://blog.csdn.net/yutian_1999/article/details/103553709