使用python实现计算表达式(使用栈的思想)

使用栈实现计算表达式的思路:

  1. 通过一个index值,来遍历我们的表达式
  2. 如果我们发现扫描的是一个数字,就直接入数字栈
  3. 如果我们发现扫描的是一个符号,就分如下的情况
    1. 如果发现当前的符号栈为空,就直接入栈
    2. 如果符号栈有操作符,就进行比较,如果当前的操作符的优先级小于或者等于栈中的操作符,就需要从数字栈中pop出两个数,在符号栈中pop出一个符号,进行运算,将得到的结果,入数栈,然后将当前的操作符入符号栈,如果当前的操作符的优先级大于栈中的操作符,就直接如符号栈
  4. 当表达式扫描完毕,就书序的从数栈和符号栈中pop出相应地数和符号,并运行
  5. 最后在数栈只有一个数字,就是表达式的结果

class ArrayStack2:
    def __init__(self,masSize):
        self.maxsize = masSize
        self.stack = []
        self.top = -1

    # 判断栈是不是 满的
    def isFull(self):
        return self.top == self.maxsize - 1

    # 判断栈是不是空的
    def isEmpty(self):
        return self.top == -1

    # 将数据压入栈中
    def push(self,value):
        if self.isFull():
            print("栈已经满了!")
            return
        self.top = self.top + 1
        self.stack.append(value)

    # 将栈中的数据进行删除
    def pop(self):
        if self.isEmpty():
            print("栈已经是空的了,没法执行出栈操作!")
            return
        value = self.stack.pop()
        self.top = self.top - 1
        return value

    # 显示栈的内容,需要先从栈顶显示数据
    def showStack(self):
        if self.isEmpty():
            print("栈已经是空的了,没法执行显示操作!")
            return
        i = self.top
        while i > -1:
            print("栈中存在的数据:",self.stack[i])
            i = i -1

    # 返回运算法的优先级  有程序员决定  优先级使用数字来表示,数字越大优先级越高
    def priority(self,oper):
        if (oper == "*" or oper == "/"):
            return 1
        elif (oper == "+" or oper == "-"):
            return 0
        else:
            return -1

    # 判断是不是一个运算法
    def isOper(self,val):
        return val == "*" or val == "/" or val == "+" or val =="-"

    # 进行计算
    def cal(self,num1,num2,oper):
        if oper == "+":
            return num1 + num2
        elif oper == "-":
            return num2 - num1 # 注意顺序
        elif oper == "*":
            return num1 * num2
        elif oper == "/":
            return num2 / num1

    # 只返回最后的一个元素,但是并不是删除最后 一个元素
    def peek(self):
        return self.stack[self.top]

class Calculator:
    def __init__(self,expresion = "30+2*6-22"):
        self.expresion = expresion
        # 创建两个栈  一个数字栈,一个符号栈
        self.numstack1 = ArrayStack2(10)
        self.operstack2 = ArrayStack2(10)
        self.num1 = 0
        self.num2 = 0
        self.oper = 0
        self.res = 0
        self.keepnum = ""
        self.flag = 0  # 作为多位数的标志位
        self.index = 1  # 用于检查每个数字字符串后面是不是还有字符串

    def cal1(self):
        data = 0
        while data < len(self.expresion):
        #for data in range(len(self.expresion)):
            print(self.expresion[data])
            if self.expresion[data] == " ": # 因为有时候会产生空格
                continue
            if self.operstack2.isOper(self.expresion[data]):
                if self.operstack2.isEmpty():
                    # 直接入栈
                    self.operstack2.push(self.expresion[data])
                    # 如果不为空,就有其他操作,就是比较运算法的优先级
                else:
                    if (self.operstack2.priority(self.expresion[data]) <= self.operstack2.priority(self.operstack2.peek())):
                        # 此时从数栈中取出来两个数,然后进行计算
                        self.num1 = self.numstack1.pop()
                        self.num2 = self.numstack1.pop()
                        self.oper = self.operstack2.pop()
                        self.res = self.numstack1.cal(self.num1,self.num2,self.oper)
                        self.numstack1.push(self.res)
                        self.operstack2.push(self.expresion[data])
                    else:
                        # 如果当前的优先级大于栈中的运算符
                        self.operstack2.push(self.expresion[data])
            else:
                self.keepnum = self.expresion[data]

                while True:
                    if data + self.index <= len(self.expresion) - 1:
                        if (self.operstack2.isOper(self.expresion[data+self.index])) == False:
                            self.flag = 1
                            self.keepnum = self.keepnum + self.expresion[data+self.index]
                            self.index = self.index + 1
                        else:
                            break
                    else:
                        break
                self.numstack1.push(int(self.keepnum))
                self.keepnum = ""
                #self.numstack1.push(int(self.expresion[data]))
            if self.flag:
                data =data + self.index
                self.index = 1
                self.flag = 0
            else:
                data = data + 1
            print("看看数字栈中的数:", self.numstack1.showStack())
        while True:
            if self.operstack2.isEmpty():
                break
            self.num1 = self.numstack1.pop()
            self.num2 = self.numstack1.pop()
            self.oper = self.operstack2.pop()
            self.res = self.numstack1.cal(self.num1, self.num2,self.oper)
            self.numstack1.push(self.res)
        print("看看数字栈中最后的的数:",self.numstack1.showStack())
        print(self.numstack1.pop())

if __name__ == '__main__':
    cal = Calculator()
    cal.cal1()

  • 3
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值