四种线性结构之栈Stack

四种线性结构 之栈Stack

栈Stack
队列Queue
双端队列Deque
列表List
这些线性结构是应用最广泛的数据结构,它们出现在各种算法中,解决各种重要的问题

栈Stack

一种有次序的数据项集合,在栈中,数据项的加入和移除都仅发生在同一端,这一段叫做栈的“顶Top”,另一端叫栈的“底base”
距离栈底越近的数据项,留在栈中的时间就越长,而最新加入栈的数据项会被最先移除,这种次序通常称为“先进后出LIFO”,即Last in First out。这是一种基于数据项保存时间的次序,时间越短的离栈顶越近,而时间越长的离栈底越近

进栈和出栈的次序正好相反

栈的特性:反转次序

这种访问次序反转的特性,举例如:浏览器的“后退back”按钮,最先back的是最近访问的网页,Word里的undo按钮最先撤销的是最后执行的操作

在Python中抽象数据类型栈有如下操作:

Stack(): 创建一个空栈,不包含任何数据项
push(item): 将item加入栈顶,无返回值
pop(): 将栈顶数据移除,并返回,栈被修改
peek(): “窥视”栈顶数据项,返回栈顶的数据项,但不移除,栈不被修改
isEMpty(): 返回栈是否为空栈
size(): 返回栈中有多少个数据项

用Python实现ADT Stack

由于Stack是一个数据集,所以可以采用Python的原生数据集(List和dict)来实现。我们选用最常用的数据集List来实现
可以将List的任意一段(index=0或者-1)设置为栈顶
我们选用List的末端(index=-1)作为栈顶,这样栈的操作就可以通过对List的append和pop来实现
在这里插入图片描述

栈的应用1:简单括号匹配

构造括号匹配识别算法:从左到右扫描括号串,最新打开的左括号,应该匹配最先遇到的右括号,这样第一个左括号(最早打开的),就应该匹配最后一个右括号(最后遇到的),这种次序反转的识别,正好符合栈的特性
在这里插入图片描述

暴力判断:
from pythonds.basic.stack import Stack

def parChecker1(symbolString):
    s = Stack()
    balanced = True
    index = 0
    while index < len(symbolString) and balanced:
        symbol = symbolString[index]
        if symbol == "(" or symbol == "["  or symbol == "{" :
            s.push(symbol)
        elif symbol == ")":
            if s.isEmpty() or s.peek() == "[" or s.peek() == "{":
                balanced = False
            else:
                s.pop()
        elif symbol == "]":
            if s.isEmpty() or s.peek() == "(" or s.peek() == "{":
                balanced = False
            else:
                s.pop()
        elif symbol == "}":
            if s.isEmpty() or s.peek() == "(" or s.peek() == "[":
                balanced = False
            else:
                s.pop()
                
        index = index + 1

    if balanced and s.isEmpty():
        return True
    else:
        return False
匹配判断:
def parChecker2(symbolString):
    s = Stack()
    balanced = True
    index = 0
    while index < len(symbolString) and balanced:
        symbol = symbolString[index]
        if symbol in "([{" :
            s.push(symbol)
        elif symbol in ")]}":
            if s.isEmpty() :
                balanced = False
            else:
                top = s.pop()
                if not matches(top,symbol):
                    balanced = False
        index = index + 1

    if balanced and s.isEmpty():
        return True
    else:
        return False

def matches(open, close):
    opens = "([{"
    closes = ")]}"
    return opens.index(open) == closes.index(close)
print(parChecker2("(5*(4+3){[]}())"))

检查一下输出结果正确

栈的应用2:十进制转换二进制

利用除以2得到一个十进制数的二进制表达形式,在除以2的过程中,得到的余数是从低位到高位的次序,而输出则是从高到低,所以需要一个次序反转,因此需要用到栈。

def matches(open, close):
    opens = "([{"
    closes = ")]}"
    return opens.index(open) == closes.index(close)
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值