栈的基本原理及实现

栈是一种后进先出(LIFO)的线性数据结构,仅允许在表尾进行插入和删除操作。本文介绍了栈的基本原理,包括入栈和出栈操作的伪代码及实现,并探讨了栈在括号匹配、逆波兰表达式和数制转换等实际应用中的作用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

原理

栈(stack)又称堆栈,它是一种运算受限的线性表。限定仅在表尾进行插入和删除操作。这一端被称为栈顶,相对地,把另一端称为栈底。向一个栈插入新元素又称进栈、入栈或者是压栈,它是把新元素放到栈顶元素的上面,使之称为新的栈顶元素;从一个栈删除一个元素又称出栈或者是退栈,它是把栈顶元素删除掉,使其相邻的元素称为新的栈顶元素。当栈中没有任何元素时称为空栈。

由于栈这种数据结构只允许在一端进行操作,又按照后进先出(LIFO, Last In First Out)的原理运作。因此栈又称后进先出(LIFO, Last In First Out)或先进后出(FILO, First In Last Out)的线性表。

实现

入栈操作
伪代码如下:

  • 如果当前栈的大小小于栈的极限容量,则将元素压进栈中。

具体实现代码如下:

    def push(self, data):
        if len(self.stack) >= self.limit:
            raise IndexError('超出栈容量极限')
        self.stack.append(data)

出栈操作
伪代码如下:

  • 如果栈非空,则取出栈顶元素并返回。

具体实现代码如下:

    def pop(self):
        if self.stack:
            return self.stack.pop()
        else:
            raise IndexError('从空栈中弹出')

完整代码如下:

class Stack(object):

    def __init__(self, limit=10):
        self.stack = []
        self.limit = limit

    def push(self, data):
        if len(self.stack) >= self.limit:
            raise IndexError('超出栈容量极限')
        self.stack.append(data)

    def pop(self):
        if self.stack:
            return self.stack.pop()
        else:
            raise IndexError('从空栈中弹出')
	# 获取栈顶元素
    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 == ')':
            if stack.is_empty():
                return False
            stack.pop()
        else:
            raise RuntimeError('非法字符')
    return stack.is_empty()

逆波兰表达式
伪代码如下:

  • 如果当前字符是数字,则把数字压入栈中。
  • 如果当前字符是运算符,则从栈中弹出两个元素,根据运算符做相应运算后,将结果压入栈中。
  • 当所有字符处理完毕后,堆栈上包含的数值就是表达式的运算结果。

具体实现代码如下:

def reversePolishExpr(expr = '12,4,*,1,2,+,+'):
    Stack = []
    Div = lambda x, y: int(x/y) 
    Opr = {'^':operator.pow, '*':operator.mul, '/':Div, '+':operator.add, '-':operator.sub}
    exprs = expr.split(',')
    for x in exprs:
        if x in r'+*/^-':
            if len(Stack) < 2:
                raise RuntimeError('栈中的元素个数必须大于或等于两个')
            B = Stack.pop()
            A = Stack.pop()
            Stack.append(str(Opr[x](int(A), int(B))))
        else:
            Stack.append(x)
            
    return int(Stack[0])

数制转换
伪代码如下:

  • 如果N不等于零,则将N % 2压入栈中,N等于N / 2。

具体实现代码如下:

def conversion(N, K = 2):
    digits = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'
    Stack = []

    while N > 0:
        Stack.append(N % K)
        N //= K

    res = ''

    while bool(Stack):
        res = res + digits[Stack.pop()]

    return res
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值