Search code examples
pythonsympysymbolic-math

SymPy does not recognize equal values


Simple calculations in SymPy quickly create unwieldy results like the three should_be values below.
Comparisons to the correct values give False (although math.isclose gives True).

from sympy import sqrt
phi = (1 + sqrt(5)) / 2
should_be_phi = -(1/2 + sqrt(5)/2)**2 + (1/2 + sqrt(5)/2)**3
should_be_half = -sqrt(5)/8 + 1/8 + (1/2 + sqrt(5)/2)**2/4
should_be_one = -sqrt(5)/4 + 1/4 + (1/2 + sqrt(5)/2)**2/2
print(should_be_phi == phi, should_be_half == 1/2, should_be_one == 1)

These are the same formulas formatted by Wolfram Alpha:
phi: enter image description here      half: enter image description here      one: enter image description here
should_be_phi was created as phi**3 - phi**2 btw.

Currently I always copy these monstrosities to Wolfram Alpha to get decent formulas and to remove duplicates.

Do you also get False for each comparison? I use Python 3.6.8 and SymPy 1.4.

Is there a way do do symbolic calculations in Python that actually works?
SymPy seems to be unable to do the things it is supposedly made for.


Solution

  • I presume that what you want is for those expressions to be simplified so just use the simplify function:

    In [6]: from sympy import *
    
    In [7]: phi = (1 + sqrt(5)) / 2
    
    In [8]: should_be_phi = -(S(1)/2 + sqrt(5)/2)**2 + (S(1)/2 + sqrt(5)/2)**3
    
    In [9]: should_be_phi
    Out[9]: 
              2           3
      ⎛1   √5⎞    ⎛1   √5⎞ 
    - ⎜─ + ──⎟  + ⎜─ + ──⎟ 
      ⎝2   2 ⎠    ⎝2   2 ⎠ 
    
    In [10]: simplify(should_be_phi)
    Out[10]: 
    1   √5
    ─ + ──
    2   2 
    

    Note that you should use S(1)/2 rather than 1/2 which gives a float.

    If you want to compare expressions then the obvious way would be to use == but that is for "structural equality" in SymPy. What that means is that expr1 == expr2 will give True only when the expressions are in the exact same form. If you want to test for mathematical equality then you should use Eq(lhs, rhs) or simplify(lhs-rhs):

    In [11]: should_be_phi == phi    # Expressions are not in the same form
    Out[11]: False
    
    In [12]: Eq(should_be_phi, phi)
    Out[12]: True
    
    In [13]: simplify(should_be_phi - phi)
    Out[13]: 0
    

    Is there a way do do symbolic calculations in Python that actually works? SymPy seems to be unable to do the things it is supposedly made for.

    Unlike Wolfram Alpha, SymPy is not designed to be usable or understandable to someone who has not read any of the documentation. Your questions above would be answered if you had read the first few pages of the SymPy tutorial: https://docs.sympy.org/latest/tutorial/index.html#tutorial