简体   繁体   English

为什么 SymPy 不将 (-x**3)**(2/3) 简化为 x**2?

[英]Why does SymPy not simplify (-x**3)**(2/3) to x**2?

I'm trying to use SymPy to evaluate the following integral:我正在尝试使用 SymPy 来评估以下积分: $$ \\int_{较低}^{0} $$

When evaluating by hand, the answer is −½ log(28).手动评估时,答案是 -½ log(28)。

My work matches up with SymPy until I integrate with respect to x :我的工作与 SymPy 匹配,直到我对x整合:

x, y = sp.symbols('x y', real=True)
z = 1 / (sp.root(y, 3)*(x**3+1))
iz = z.integrate((y, -x**3, 0)) # integrate with respect to y
print(iz)
# -3*(-x**3)**(2/3)/(2*(x**3 + 1))
iiz = iz.integrate((x, 0, 3)) # integrate with respect to x
print(iiz)
# -3*Integral((-x**3)**(2/3)/(x**3 + 1), (x, 0, 3))/2
print(sp.N(iiz))
# 0.833051127543801 - 1.4428868782084*I

It seems what's throwing SymPy off is (-x**3)**(2/3) .似乎让 SymPy 失败的是(-x**3)**(2/3) This should simplify to x**2 but SymPy doesn't think so.这应该简化为x**2但 SymPy 不这么认为。 Manually simplifying, produces the same answer I got by hand:手动简化,产生与我手动得到的相同答案:

print( sp.integrate(-3*x**2/(2*(x**3 + 1)), (x, 0, 3)) )
# -log(28)/2

Is there a better way to approach this?有没有更好的方法来解决这个问题?

Your problem is that sympy.root by default returns the principal root, not the real root.您的问题是sympy.root默认返回主体根,而不是真正的根。 To avoid this, you can use the third optional argument of sympy.root to specify that you would like the real root.为了避免这种情况,您可以使用sympy.root的第三个可选参数来指定您想要真正的根。 The following produces the desired result:以下产生了所需的结果:

import sympy as sp

x, y = sp.symbols('x y', real=True)
z = 1 / (sp.root(y,3,1)*(x**3+1))
iz = z.integrate((y, -x**3, 0))
iiz = iz.integrate((x, 0, 3))
print(iiz)
# -log(28)/2

To somewhat address your titular question, (-x**3)**(2/3) is actually (-x**3)**0.666666666666667 because that's a Python fraction you have there.为了稍微解决您的名义问题, (-x**3)**(2/3)实际上是(-x**3)**0.666666666666667因为这是您在那里的 Python 分数。 To have something closer to what you want, you need to do:要获得更接近您想要的东西,您需要执行以下操作:

import sympy as sp
x = sp.symbols('x', positive=True)
solution = (-x**3)**sp.Rational(2,3)
print(solution)
# (-1)**(2/3)*x**2

In general, I would recommend to avoid rational powers unless you really need to account for them in all their multiple solutions, complexity, etc.一般而言,我建议避免使用理性权力,除非您确实需要在所有多种解决方案、复杂性等中考虑到它们。

In my isympy session: SymPy 1.6.2在我的isympy会话中:SymPy 1.6.2

In [131]: z = 1 / (root(y,3)*(x**3+1))

In [132]: iz = z.integrate((y, -x**3, 0))

In [133]: iiz = iz.integrate((x,0,3))

In [134]: iiz
Out[134]: 
     2/3         
-(-1)   ⋅log(28) 
─────────────────
        2        

In [135]: N(iiz)
Out[135]: 0.833051127543801 - 1.4428868782084⋅ⅈ

In [136]: abs(iiz)
Out[136]: 
log(28)
───────
   2   

The root docs talk about returning the principal root, and in addition to providing a k parameter, suggest using real_root : root文档讨论返回主根,除了提供k参数外,建议使用real_root

In [137]: z = 1 / (real_root(y,3)*(x**3+1))

In [138]: iz = z.integrate((y, -x**3, 0))

In [139]: iiz = iz.integrate((x,0,3))

In [140]: iiz
Out[140]: 
-log(28) 
─────────
    2    

In [141]: N(iiz)
Out[141]: -1.66610225508760

So evidently the double integral has multiple solutions, depending on the root.所以显然二重积分有多个解,这取决于根。 Looks like they all have the same magnitude.看起来它们都具有相同的量级。 That sounds reasonable, but my complex math studies were in the distant past, so I can't provide a theoretical justification.这听起来很合理,但我复杂的数学研究是在遥远的过去,所以我无法提供理论上的理由。

and with k=2 we get a third solution:k=2我们得到第三个解决方案:

In [146]: z = 1 / (root(y,3,2)*(x**3+1))

In [147]: iz = z.integrate((y, -x**3, 0))

In [148]: iiz = iz.integrate((x,0,3))

    In [149]: iiz
    Out[149]: 
    3 ____        
    ╲╱ -1 ⋅log(28)
    ──────────────
          2     

So there are 3 solutions in the complex plane, with multipliers, -1, (-1)**(1/3), -(-1)**(2/3) , and the same magnitude.所以在复平面中有 3 个解,具有乘数, -1, (-1)**(1/3), -(-1)**(2/3) ,并且大小相同。

-1.66610225508760
0.833051127543801 - 1.4428868782084⋅ⅈ
0.833051127543801 + 1.4428868782084⋅ⅈ

If we introduce an integer symbol k into z :如果我们在z引入一个整数符号k

In [158]: z = 1 / (root(y,3,k)*(x**3+1))

In [159]: z
Out[159]: 
      -2⋅k    
      ─────   
        3     
  (-1)        
──────────────
3 ___ ⎛ 3    ⎞
╲╱ y ⋅⎝x  + 1⎠

the double integral becomes:二重积分变为:

In [164]: iiz =z.integrate((y, -x**3,0)).integrate((x,0,3))

In [165]: iiz
Out[165]: 
             -2⋅k          
             ─────         
     2/3       3           
-(-1)   ⋅(-1)     ⋅log(28) 
───────────────────────────
             2             

and doing iiz.subs({k:0}) etc, produces the above complex solutions.并做iiz.subs({k:0})等,产生上述复杂的解决方案。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM