栈是一种受限的线性表,我们规定:栈只能在表尾进行插入或者删除,由此可知,栈有着先进后出的特性,栈一般拥有入栈(push)与出栈(pop)操作
括号匹配任务描述: 检查一个字符串的括号是否匹配. 所谓匹配, 是指每个左括号有相应的一个右括号与之对应, 且左括号不可以出现在右括号右边. 可以修改测试字符串, 检查不同情况下的运行.
package com.day07;
/*
* 顺序栈的实现
* 栈的应用之括号匹配
*/
public class day07_charStack {
/**
* MAX 栈的最大容量 默认记为10
* deep 栈当前的容量
* data char类型的数组
*/
public static final int MAX = 10;
char data[];
int deep;
/**
* 初始化栈 deep 设为0
*/
public day07_charStack() {
data = new char[MAX];
deep = 0;
} //of day07_charStack()
/**
* 入栈操作 需要判断栈是否已满
* @param paraValue 入栈的元素
* @return 布尔类型返回值
*/
public boolean push(char paraValue) {
if (deep == MAX) {
System.out.println("栈满");
return false;
} // of if
data[deep] = paraValue;
deep++;
return true;
} // of push
/**
* 出栈操作 需要判断栈是否为空
* @return char类型的返回值
*/
public char pop() {
if (deep == 0) {
System.out.println("空");
return ' ';
} // of if
deep--;
return data[deep];
} // of pop
public void reset() {
deep = 0;
} // of reset
/**
* 重写toString方法
* @return String类型的返回值
*/
@Override
public String toString() {
String result = "";
if (deep == 0) {
return "栈空";
} //of if
for (int i = 0; i < deep; i++) {
result += data[i];
} // of for i
return result;
} // of toString
/**
* 括号匹配
* @param paraString 需要验证的字符串
* @return 布尔类型的返回值
*/
public static boolean bracketMatching(String paraString) {
char tempChar, tempPopedChar;
day07_charStack tempStcack = new day07_charStack();
tempStcack.push('#');
for (int i = 0; i < paraString.length(); ++i) {
tempChar = paraString.charAt(i);
switch (tempChar) {
case '(':
case '[':
case '{':
tempStcack.push(tempChar);
break;
case ')':
tempPopedChar = tempStcack.pop();
if (tempPopedChar != '(') {
return false;
} // of if
break;
case ']':
tempPopedChar = tempStcack.pop();
if (tempPopedChar != '[') {
return false;
} // of if
break;
case '}':
tempPopedChar = tempStcack.pop();
if (tempPopedChar != '{') {
return false;
} // of if
break;
default:
} //of swhich
} // of for i
if (tempStcack.pop() != '#') {
return false;
} // of if
return true;
} // of bracketMatching
/**
* 程序入口
* @param args 无
*/
public static void main(String args[]) {
day07_charStack tempStack = new day07_charStack();
for (char ch = 'a'; ch < 'm'; ch++) {
tempStack.push(ch);
System.out.println("The current stack is: " + tempStack);
} // Of for i
char tempChar;
for (int i = 0; i < 12; i++) {
tempChar = tempStack.pop();
System.out.println("Poped: " + tempChar);
System.out.println("The current stack is: " + tempStack);
} // Of for i
boolean tempMatch;
String tempExpression = "[2 + (1 - 3)] * 4";
tempMatch = bracketMatching(tempExpression);
System.out
.println("Is the expression " + tempExpression + " bracket matching? " + tempMatch);
tempExpression = "( ) )";
tempMatch = bracketMatching(tempExpression);
System.out
.println("Is the expression " + tempExpression + " bracket matching? " + tempMatch);
tempExpression = "()()(())";
tempMatch = bracketMatching(tempExpression);
System.out
.println("Is the expression " + tempExpression + " bracket matching? " + tempMatch);
tempExpression = "({}[])";
tempMatch = bracketMatching(tempExpression);
System.out
.println("Is the expression " + tempExpression + " bracket matching? " + tempMatch);
tempExpression = ")(";
tempMatch = bracketMatching(tempExpression);
System.out
.println("Is the expression " + tempExpression + " bracket matching? " + tempMatch);
} // of main
} // of day07_charStack
运行结果:
总结:
- 括号匹配作为栈的经典应用之一,如果以人的视角来看,我们可以很轻松的看出结果,但是机器是没有全局视野的,而栈的特性刚好能处理这种高度对称的成对数据,我们可以让其中的一半先进栈里,匹配成功出栈,由于数据是高度对称的,另一半来匹配时栈尾的元素必然能对上,否则匹配失败。
- 以前第一次接触栈的时候,不明白为什么会有这么奇怪的数据结构,究其原因还是由于站在人的视角,只有反复揣摩经典的数据结构,才能更加贴近机器思维,在之后的算法实现才能想到用什么数据结构。