用符号表示符号特征值

时间:2017-09-22 09:31:32

标签: python-2.7 sympy symbolic-math eigenvalue

我试图计算大小为M的符号复杂矩阵3x3的特征值。在某些情况下,eigenvals()完美无缺。例如,以下代码:

import sympy as sp

kx = sp.symbols('kx')
x = 0.

M = sp.Matrix([[0., 0., 0.], [0., 0., 0.], [0., 0., 0.]])
M[0, 0] = 1. 
M[0, 1] = 2./3.
M[0, 2] = 2./3.
M[1, 0] = sp.exp(1j*kx) * 1./6. + x
M[1, 1] = sp.exp(1j*kx) * 2./3.
M[1, 2] = sp.exp(1j*kx) * -1./3.
M[2, 0] = sp.exp(-1j*kx) * 1./6.
M[2, 1] = sp.exp(-1j*kx) * -1./3.
M[2, 2] = sp.exp(-1j*kx) * 2./3.

dict_eig = M.eigenvals()

返回{3}正确的复杂符号特征值M。但是,当我设置x=1.时,我收到以下错误:

  

引发MatrixError("无法计算{}" .format(self)的特征值

我还尝试按如下方式计算特征值:

lam = sp.symbols('lambda')
cp = sp.det(M - lam * sp.eye(3))
eigs = sp.solveset(cp, lam)

但在任何情况下它都会返回ConditionSet,即使eigenvals()可以完成这项工作。

有没有人知道如何正确解决这个特征值问题,x的任何值?

1 个答案:

答案 0 :(得分:2)

你对M的定义使得SymPy的生活太难了,因为它引入了浮点数。当您需要符号解决方案时,应避免浮动。这意味着:

  • 而不是1./3.(Python的浮点数)使用sp.Rational(1, 3)(SymPy的有理数)或sp.S(1)/3,它具有相同的效果但更容易键入。
  • 而不是1j(Python的虚构单位)使用sp.I(SymPy的虚构单位)
  • 而不是x = 1.,写x = 1(Python 2.7的习惯和SymPy很糟糕)。

通过这些更改,solvesetsolve会找到特征值,尽管solve会让它们更快。此外,您可以创建一个Poly对象并将roots应用于它,这可能是最有效的:

M = sp.Matrix([
    [
        1,
        sp.Rational(2, 3),
        sp.Rational(2, 3),
    ],
    [
        sp.exp(sp.I*kx) * sp.Rational(1, 6) + x,
        sp.exp(sp.I*kx) * sp.Rational(1, 6),
        sp.exp(sp.I*kx) * sp.Rational(-1, 3),
    ],
    [
        sp.exp(-sp.I*kx) * sp.Rational(1, 6),
        sp.exp(-sp.I*kx) * sp.Rational(-1, 3),
        sp.exp(-sp.I*kx) * sp.Rational(2, 3),
    ]
])
lam = sp.symbols('lambda')
cp = sp.det(M - lam * sp.eye(3))
eigs = sp.roots(sp.Poly(cp, lam))

from sympy import *比输入所有这些sp更容易。)

即使进行了上述修改,我也不太清楚为什么SymPy的特征方法报告失败。正如您所看到的in the source,它没有上述代码所做的更多:在特征多项式上调用roots。差异似乎与创建此多项式的方式有关:M.charpoly(lam)返回

PurePoly(lambda**3 + (I*sin(kx)/2 - 5*cos(kx)/6 - 1)*lambda**2 + (-I*sin(kx)/2 + 11*cos(kx)/18 - 2/3)*lambda + 1/6 + 2*exp(-I*kx)/3, lambda, domain='EX')

神秘(对我而言)domain='EX'。随后,roots的应用程序返回{},找不到根。看起来像实施的缺陷。