【问题标题】:Preventing a multiplication expression evaluating in Sympy防止在 Sympy 中计算乘法表达式
【发布时间】:2017-02-27 12:52:33
【问题描述】:

我正在生成一个包含两个分数的表达式,并想用 LaTeX 将整个表达式漂亮地打印出来,然后放在工作表上。

例如形式:

(5/7) * (3/4). 

但是,当我执行以下操作时:

fract1 = sympy.sympify(Fraction(5,7))
fract2 = sympy.sympify(Fraction(3,4))
expression = sympy.Mul(fract1,fract2,evaluate=False)

返回

5*3/(7*4)

很明显,它是结合分数,但不是实际评估,但我希望能够以适合作为数学工作表问题的格式生成它。

【问题讨论】:

  • 是最终目标只是打印还是您希望稍后评估表达式?
  • 是的,我想先打印出来,然后再评估。
  • 示例正在添加到 SymPy 的教程中:github.com/sympy/sympy/pull/12232

标签: python python-3.x numpy latex sympy


【解决方案1】:

下一个 SymPy 版本将有 UnevaluatedExpr:

In [4]: uexpr = UnevaluatedExpr(S.One*5/7)*UnevaluatedExpr(S.One*3/4)

In [7]: uexpr
Out[7]: 5/7⋅3/4

要发布和评估它,只需使用.doit()

In [8]: uexpr.doit()
Out[8]: 
15
──
28

LaTeX 输出如下:

In [10]: print(latex(uexpr))
\frac{5}{7} \frac{3}{4}

此功能从 SymPy 1.1 开始可用。请参阅documentation to find out more

【讨论】:

  • 谢谢!这是预先计划好的还是为了回答问题?
  • 该功能已在几个月前添加到主开发分支。 SymPy 教程中的文档是针对这个问题添加的(它丢失了)。
【解决方案2】:

非常老套的方法(仅适用于您的两个分数的情况):

def print_fractions(expr):
    print("({}) * ({})".format(*expr.args))

像这样工作:

In:  expr = sympy.Mul(sympy.S("5/7"), sympy.S("3/4"), evaluate=False)
In:  expr
Out: 5*3/(7*4)
In:  print_fractions(expr)
Out: (5/7) * (3/4)

您可以通过srepr 检查分数实际上没有在expr 中合并,这只是 sympy 决定打印它的方式:

In:  sympy.srepr(expr)
Out: 'Mul(Rational(5, 7), Rational(3, 4))'

另一种方法是扩展sympy.Mul 覆盖__str__ 方法:

class MyMul(sympy.Mul):
    def __str__(self):
        return "({}) * ({})".format(*self.args)

那么你将拥有:

In:  expr = MyMul(sympy.S("5/7"), sympy.S("3/4"), evaluate=False)
In:  print(expr)
Out: (5/7) * (3/4)

开斋节:如何让latex() 工作

又是骇人听闻的方法,但是:

class MyMul(Mul):
    def _latex(self, _):
        return r"\left({} \cdot {}\right)".format(*map(latex, self.args))

现在:

In:  a = S("5/7")
In:  b = S("3/4")
In:  c = MyMul(a, b, evaluate=False)
In:  print(latex(c))
Out: \left(\frac{5}{7} \cdot \frac{3}{4}\right)

当然,您可以在上面_latex 的定义中更改您输出的确切内容。

【讨论】:

  • 嗨,谢谢。它可以工作,但是一旦涉及到 Latex 就会出现问题,因为 sympy.latex 不适用于创建的字符串。
  • @benjo456 也没有什么能阻止你破解类的_latex 方法。我现在将其添加到答案中。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-06-14
  • 1970-01-01
  • 2018-02-02
  • 1970-01-01
相关资源
最近更新 更多