Python利用后缀表达式实现计算器功能

Owen
Owen
发布时间:2026-10-14| 4人浏览过
原创

本文介绍如何使用Python通过栈结构实现计算器功能。详细解析前缀、中缀及后缀表达式的区别,重点阐述中缀表达式转换为后缀表达式的算法逻辑,包括优先级判断与栈操作。最后提供完整的Python代码示例,展示如何遍历表达式、处理运算符优先级及计算最终结果,帮助开发者理解表达式求值的线性处理过程。

本文分享了一个使用Python实现计算器功能的具体代码案例,供读者参考学习。

前缀表达式

在前缀表达式中,运算符位于操作数的前面。

例如,中缀表达式 `1 + (2 + 3) * 4 - 5` 对应的前缀表达式为 `- + 1 * + 2 3 4 5`。

前缀表达式的计算逻辑与后缀表达式类似,区别在于扫描方向是从右向左进行。

中缀表达式

中缀表达式中运算符位于操作数中间,计算时需考虑运算符的优先级。

例如 `1+2*3-5`,需要先计算 `2*3`,再处理加减法。

后缀表达式

后缀表达式中运算符位于操作数之后,计算时无需考虑优先级,只需遇到符号,就将该符号前面的两个数字进行运算。

例如表达式 `a b c + +` 等价于 `a + (b + c)`。

中缀表达式 `1 + (2 + 3) * 4 - 5` 转换为后缀表达式后为 `1 2 3 + 4 * + 5 -`。

由于后缀表达式无需考虑优先级,运算过程呈线性结构,因此使用栈来实现非常简便。

中缀表达式转换为后缀表达式

转换的基本规律是:运算数的相对位置保持不变,仅改变符号的位置。

例如,中缀表达式 `2 + 9 / 3 - 5` 转换为后缀表达式为 `2 9 3 / + 5 -`。

具体转换方式如下:

1. 从左到右遍历中缀表达式。 2. 若遇到运算数,直接输出。 3. 若遇到左括号,直接压入栈中(括号具有最高优先级,无需比较,入栈后其优先级降至最低,确保其他符号能正常入栈)。 4. 若遇到右括号,意味着括号结束,不断弹出栈顶运算符并输出,直到遇到左括号(左括号弹出但不输出)。 5. 若遇到运算符,将其与栈顶运算符比较优先级: - 如果当前运算符优先级高于栈顶运算符,则将其压入栈(此时该部分运算尚不能进行)。 - 如果当前运算符优先级低于或等于栈顶运算符,则将栈顶运算符弹出并输出,然后继续比较新的栈顶运算符。 (优先级低意味着前面的部分可以运算,先输出的必然是高优先级运算符;优先级相等时弹出是因为遵循从左到右的运算顺序)。 直到当前运算符优先级大于栈顶运算符或栈为空,再将当前运算符入栈。 6. 当遍历完成后,按顺序弹出栈中剩余的运算符并输出。

后缀表达式运算步骤

后缀表达式的运算步骤如下:

使用栈进行存储和处理:从左到右遍历表达式,遇到运算符时弹出相应的两个运算数,计算结果后将结果重新入栈。最终栈顶元素的值即为表达式的结果。(由于该运算是线性结构,具体实现时通常输出一个运算符就立即进行一次运算,无需像某些示意图那样存储所有输出状态。)

注意点:

有时负号 '-' 作为单目运算符出现,此时需要调整对运算数的处理逻辑。遇到其他一元运算符(如幂运算)时,处理方式类似。

Python代码示例


'''
中缀转换为后缀
'''

a = "1+(2+6/1+2)"
#a = "2+9/3-5"
# 可能出现的符号 
symbol_1 = ['+','-','*','/']
symbol_2 = ['(']
symbol_3 = [')']
# 符号的优先级
priority = {'#':-1,'(':1,'+':2,'-':2,'*':3,'/':3}
match_2 = {')':'('}
# 存储符号的栈
zhan = []
zhan.append("#")
# 结果
result = []

'''
### 这里只是对表达式进行转换
for i in a:
 # 如果是数字直接添加到结果
 if i.isdigit():
 result.append(i)
 # 如果是 + - * / 运算,则先出栈更低优先级的,然后入栈
 elif i in symbol_1:
 # 如果优先级低,则出栈所有优先级>=的符号
 while priority[i] <= priority[zhan[-1]]:
 result.append(zhan.pop())
 # 压入符号
 zhan.append(i)
 # 如果是左括号,直接压入
 elif i in symbol_2:
 zhan.append(i)
 # 如果是右括号,则出栈,直到遇到了匹配的左括号,然后吧左括号也出栈
 elif i in symbol_3:
 while zhan[-1] != match_2[i]:
 result.append(zhan.pop())
 zhan.pop()
 
result.append(zhan.pop())
print(''.join(result))

'''
# 下面通过将中缀表达式转换为后缀表达式,并进行运算
def my_operation(symbol, a, b):
 a,b = int(a),int(b)
 if symbol == '+':
 return a + b
 elif symbol == '-':
 return a - b
 elif symbol == '*':
 return a * b
 elif symbol == '/':
 return a / b

def to_operation(result, zhan):
 two = result.pop()
 one = result.pop()
 symbol = zhan.pop()
 ret = my_operation(symbol, one, two)
 print(f"{one}{symbol}{two} = {ret}")
 result.append(ret)

### 在表达式转换的时候就一边进行了运算
for i in a:
 # 如果是数字直接添加到结果
 if i.isdigit():
 result.append(i)
 # 如果是 + - * / 运算,则先出栈更低优先级的,然后入栈
 elif i in symbol_1:
 # 如果优先级低,则出栈所有优先级>=的符号
 while priority[i] <= priority[zhan[-1]]:
 to_operation(result, zhan)
 # 压入符号
 zhan.append(i)
 # 如果是左括号,直接压入
 elif i in symbol_2:
 zhan.append(i)
 # 如果是右括号,则出栈,直到遇到了匹配的左括号,然后吧左括号也出栈
 elif i in symbol_3:
 while zhan[-1] != match_2[i]:
 to_operation(result, zhan)
 zhan.pop()
 
to_operation(result, zhan)
print(result)

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持本站。

相关标签:

免责声明:本文内容仅供参考,不代表本站观点。转载或引用请注明出处。

Python 相关产品和应用

全部下载
Selenium

Selenium

4.51.0 · Windows

用于浏览器自动化和 Web 测试的 Python 工具。

scikit-learn

scikit-learn

1.9.1 · Windows

常用 Python 机器学习算法与模型评估工具库。

Black

Black

26.10.1 · Windows

强调一致性的 Python 自动代码格式化工具。

Ruff

Ruff

0.17.1 · macOS

由 Rust 编写的高速 Python 代码检查和格式化工具。

pytest

pytest

9.1.1 · Windows

简洁而强大的 Python 自动化测试框架。

FastAPI

FastAPI

0.146.0 · Windows

高性能 Python API 框架,支持类型提示和自动接口文档。

Flask

Flask

3.1.3 · Windows

轻量灵活的 Python Web 应用框架。

Django

Django

6.1.2 · Windows

成熟的 Python Web 框架,适合构建内容站点和业务系统。

Spyder

Spyder

6.1.7 · Windows

面向科学计算与数据分析的 Python 集成开发环境。

SciPy

SciPy

1.18.1 · Windows

面向科学、工程和技术计算的 Python 算法库。