You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何替换Python脚本中已弃用的parse库解决计算器Error11报错

问题根因

  • 你触发Error11的直接原因是parse库的parse.expr()调用失败,该库长期未维护,API兼容性差,没必要在这个场景下使用。
  • 原有逻辑中使用parse编译表达式再调用eval的步骤完全冗余,你计算器按钮生成的表达式本身就是合法的Python算术表达式,可直接处理。

方案1:极简适配方案(适合本地自用场景)

直接替换你的calculate函数即可,无需引入额外依赖:

def calculate():
    entire_string = display.get()
    print("ddddd "+entire_string)
    try:
        # 直接对合法算术表达式求值,去掉冗余的parse调用
        result = eval(entire_string)
        clear_all()
        display.insert(0, result)
    except Exception:
        clear_all()
        display.insert(0, "Error11")

注:本地自用的计算器不存在恶意输入风险,该方案足够稳定。

方案2:安全ast实现方案(避免eval风险)

如果需要更安全的表达式校验,使用ast库只允许合法算术操作,实现如下:
首先定义ast求值函数:

import ast
import operator

# 定义允许的运算符
ALLOWED_OPERATORS = {
    ast.Add: operator.add,
    ast.Sub: operator.sub,
    ast.Mult: operator.mul,
    ast.Div: operator.truediv,
    ast.Pow: operator.pow,
    ast.Mod: operator.mod,
    ast.USub: operator.neg
}

def safe_eval(expr):
    def _eval(node):
        if isinstance(node, ast.Constant):
            # 支持数字常量
            if isinstance(node.value, (int, float)):
                return node.value
        elif isinstance(node, ast.BinOp):
            # 二元运算
            op_type = type(node.op)
            if op_type not in ALLOWED_OPERATORS:
                raise ValueError(f"不支持的运算符: {op_type}")
            return ALLOWED_OPERATORS[op_type](_eval(node.left), _eval(node.right))
        elif isinstance(node, ast.UnaryOp):
            # 一元运算(负数等)
            op_type = type(node.op)
            if op_type not in ALLOWED_OPERATORS:
                raise ValueError(f"不支持的运算符: {op_type}")
            return ALLOWED_OPERATORS[op_type](_eval(node.operand))
        else:
            raise ValueError(f"不支持的语法: {type(node)}")
    # 解析表达式
    ast_node = ast.parse(expr, mode='eval').body
    return _eval(ast_node)

然后替换你的calculate函数:

def calculate():
    entire_string = display.get()
    print("ddddd "+entire_string)
    try:
        result = safe_eval(entire_string)
        clear_all()
        display.insert(0, result)
    except Exception:
        clear_all()
        display.insert(0, "Error11")

其他注意点

  • 你原有代码中display.insert(0, "Error11").末尾多了一个多余的点,会触发语法错误,修改时请删除。
  • 全局变量i的逻辑可以优化,无需手动计数,插入内容直接用END位置即可:display.insert(END, num),可以避免光标位置错位的问题。

内容的提问来源于stack exchange,提问作者razs

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.20 14:24:07