栈(Stack)在计算机领域是一个被广泛应用的集合,栈是线性集合,访问都严格地限制在一段,叫做顶(top)。 举个例子,栈就想一摞洗干净的盘子,你每次取一个新盘子,都是放在这一摞盘子的最上头,当你往里面添加盘子的时候,也是放在最上面,处在底部的盘子,你可能永远也用不到。 栈的最常见操作,有如下两个:
push(a) # 压入,将a压入的栈中
pop() # 弹出,将栈的最后一个元素弹出
使用堆栈检查括号字符串是否平衡
算法思想:
1.顺序扫描算数表达式(表现为一个字符串),当遇到三种类型的左括号时候让该括号进栈;
2.当扫描到某一种类型的右括号时,比较当前栈顶元素是否与之匹配,若匹配,退栈继续判断;
3.若当前栈顶元素与当前扫描的括号不匹配,则左右括号配对次序不正确,匹配失败,直接退出;
4.若字符串当前为某种类型的右括号而堆栈已经空,则右括号多于左括号,匹配失败,直接退出;
5.字符串循环扫描结束时,若堆栈非空(即堆栈尚有某种类型的左括号),则说明左括号多于右括号,匹配失败;
6.正常结束则括号匹配正确。
class Stack(object):
def __init__(self, limit=10):
self.stack = [] #存放元素
self.limit = limit #栈容量极限
def push(self, data): #判断栈是否溢出
if len(self.stack) >= self.limit:
print('StackOverflowError')
pass
self.stack.append(data) #没有溢出将data放入self.stack
def pop(self):
if self.stack:
return self.stack.pop()
else:
raise IndexError('pop from an empty stack') #空栈不能被弹出
def peek(self): #查看堆栈的最上面的元素
if self.stack:
return self.stack[-1]
def is_empty(self): #判断栈是否为空
return not bool(self.stack)
def size(self): #返回栈的大小
return len(self.stack)
def balanced_parentheses(parentheses):
stack = Stack(len(parentheses))
for parenthesis in parentheses: #字符串的每个元素
if parenthesis == '(': #如果是左括号,压栈
stack.push(parenthesis)
elif parenthesis == ')': 如果是右括号,判断栈是不是空,为空则不匹配,返回False
if stack.is_empty():
return False
stack.pop() #不为空,则左右匹配,将之前压栈的左括号弹出,进行下一个字符的匹配
return stack.is_empty() 返回布尔类型
if __name__ == '__main__':
examples = ['((()))', '((())', '(()))']
print('Balanced parentheses demonstration:\n')
for example in examples:
print(example + ': ' + str(balanced_parentheses(example)))
执行结果:
Balanced parentheses demonstration:
((())): True
((()): False
(())): False
简单的讲,就是遇见左括号,就入栈,遇见右括号:
1)先判断栈内是否有元素,没有则出现了先右后左,不平衡,返回 False
2)再判断栈顶元素是否与当前右括号匹配,若不匹配,返回 False,若匹配,删除栈顶元素,继续下一循环
最后,循环结束后,判断栈内是否有元素,有则说明左括号数量多于右括号,不平衡,不匹配。没有则说明左右平衡,返回True。
字符串反转:
def str_reverse(str):
s = Stack()
result = ''
for i in str:
s.push(i)
while not s.is_empty():
result += s.pop()
return result