栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 面试经验 > 面试问答

Python-计算字符串中的数学表达式

面试问答 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

Python-计算字符串中的数学表达式

Pyparsing
可用于解析数学表达式。特别是,
fourFn.py
显示了如何解析基本算术表达式。下面,我将fourFn重新包装为一个数字解析器类,以便于重用。

from __future__ import divisionfrom pyparsing import (Literal, CaselessLiteral, Word, Combine, Group, Optional, ZeroOrMore, Forward, nums, alphas, oneOf)import mathimport operator__author__ = 'Paul McGuire'__version__ = '$Revision: 0.0 $'__date__ = '$Date: 2009-03-20 $'__source__ = '''http://pyparsing.wikispaces.com/file/view/fourFn.pyhttp://pyparsing.wikispaces.com/message/view/home/15549426'''__note__ = '''All I've done is rewrap Paul McGuire's fourFn.py as a class, so I can use itmore easily in other places.'''class NumericStringParser(object):    '''    Most of this pre comes from the fourFn.py pyparsing example    '''    def pushFirst(self, strg, loc, toks):        self.exprStack.append(toks[0])    def pushUMinus(self, strg, loc, toks):        if toks and toks[0] == '-': self.exprStack.append('unary -')    def __init__(self):        """        expop   :: '^'        multop  :: '*' | '/'        addop   :: '+' | '-'        integer :: ['+' | '-'] '0'..'9'+        atom    :: PI | E | real | fn '(' expr ')' | '(' expr ')'        factor  :: atom [ expop factor ]*        term    :: factor [ multop factor ]*        expr    :: term [ addop term ]*        """        point = Literal(".")        e = CaselessLiteral("E")        fnumber = Combine(Word("+-" + nums, nums) +    Optional(point + Optional(Word(nums))) +    Optional(e + Word("+-" + nums, nums)))        ident = Word(alphas, alphas + nums + "_$")        plus = Literal("+")        minus = Literal("-")        mult = Literal("*")        div = Literal("/")        lpar = Literal("(").suppress()        rpar = Literal(")").suppress()        addop = plus | minus        multop = mult | div        expop = Literal("^")        pi = CaselessLiteral("PI")        expr = Forward()        atom = ((Optional(oneOf("- +")) +      (ident + lpar + expr + rpar | pi | e | fnumber).setParseAction(self.pushFirst))     | Optional(oneOf("- +")) + Group(lpar + expr + rpar)     ).setParseAction(self.pushUMinus)        # by defining exponentiation as "atom [ ^ factor ]..." instead of        # "atom [ ^ atom ]...", we get right-to-left exponents, instead of left-to-right        # that is, 2^3^2 = 2^(3^2), not (2^3)^2.        factor = Forward()        factor << atom +  ZeroOrMore((expop + factor).setParseAction(self.pushFirst))        term = factor +  ZeroOrMore((multop + factor).setParseAction(self.pushFirst))        expr << term +  ZeroOrMore((addop + term).setParseAction(self.pushFirst))        # addop_term = ( addop + term ).setParseAction( self.pushFirst )        # general_term = term + ZeroOrMore( addop_term ) | oneOrMore( addop_term)        # expr <<  general_term        self.bnf = expr        # map operator symbols to corresponding arithmetic operations        epsilon = 1e-12        self.opn = {"+": operator.add,         "-": operator.sub,         "*": operator.mul,         "/": operator.truediv,         "^": operator.pow}        self.fn = {"sin": math.sin,        "cos": math.cos,        "tan": math.tan,        "exp": math.exp,        "abs": abs,        "trunc": lambda a: int(a),        "round": round,        "sgn": lambda a: abs(a) > epsilon and cmp(a, 0) or 0}    def evaluateStack(self, s):        op = s.pop()        if op == 'unary -': return -self.evaluateStack(s)        if op in "+-*/^": op2 = self.evaluateStack(s) op1 = self.evaluateStack(s) return self.opn[op](op1, op2)        elif op == "PI": return math.pi  # 3.1415926535        elif op == "E": return math.e  # 2.718281828        elif op in self.fn: return self.fn[op](self.evaluateStack(s))        elif op[0].isalpha(): return 0        else: return float(op)    def eval(self, num_string, parseAll=True):        self.exprStack = []        results = self.bnf.parseString(num_string, parseAll)        val = self.evaluateStack(self.exprStack[:])        return val你可以这样使用nsp = NumericStringParser()result = nsp.eval('2^4')print(result)# 16.0result = nsp.eval('exp(2^4)')print(result)# 8886110.520507872


转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/456667.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号