SymPy中的向量和矩阵

SymPy 中的向量和矩阵

Vectors and Matrice in SymPy

准备工作:

from sympy import *
init_printing()
a,b,c,d,e,f,g,h,i = symbols('a:i') # neat shorthand for multiple symbols!

带符号的矩阵

1、一般用矩阵类 Matrix([[],[]]) 生成可以改变的矩阵(mutable matrix)

A = Matrix([[a,b,c],[d,e,f]])
A
A[i,j]  # a(i,j), i=0,1,..., j=0,1,...
A[:,0], A[1,:] # 第一列向量j=0,第二行向量i=1
B = A[:,0:2]
B[0,0] = i

B = [ i b d e ] B=\begin{bmatrix} i & b\\ d & e \end{bmatrix} B=[idbe]

2、还可以简便操作,提供行列数和数列

B = Matrix(2,3,[1,2,3,4,5,6])

B = [ 1 2 3 4 5 6 ] B=\begin{bmatrix} 1 & 2 & 3\\ 4 & 5 & 6 \end{bmatrix} B=[142536]

3、通过二元函数来定义矩阵

>>> B=Matrix(3,4,lambda i,j: 1-(i+j)%2)

B = [ 1 0 1 0 0 1 0 1 1 0 1 0 ] B=\begin{bmatrix} 1 & 0 & 1 & 0\\ 0 & 1 & 0 & 1\\ 1 & 0 & 1 & 0 \end{bmatrix} B=101010101010

4、用命令 ImmutableMatrix() 生成不可以更改的矩阵(immutable matrix)

C = ImmutableMatrix([[a, b,],[c, d]])
C[0, 0] = i # 报错,不可更改矩阵元素的值

5、如何得到矩阵的行列数

获取矩阵属性值:行数、列数 M.rows, M.cols, M.shape

>>> A.rows, A.cols, A.shape #(行数=2, 列数=3, 行列数=(2, 3))

6、转置矩阵(Transpose of a matrix)

A.T

A = [ a d b e c f ] A=\begin{bmatrix} a & d\\ b & e\\ c & f \end{bmatrix} A=abcdef

7、行向量 row vector 和列向量 column vector

单独一行或一列就是行向量或列向量。
没有特别定义行向量和列向量,同样用Matrix命令来定义。

Matrix([[a, b]]) #定义行向量 [ a b ] [a b] [ab]
Matrix([[c], [d]]) 或者 Matrix([c,d]) #定义列向量 [ c d ] \left [\begin{array}{l} c \\ d \end{array}\right ] [cd]

RVector = Matrix([[a,b,c]) # 行向量
CVector1 = Matrix([[c],[d],[e]]) # 列向量1
CVector2 = Matrix([c,d,e]) # 列向量2

R V e c t o r = [ a , b , c ] RVector = [a,b,c] RVector=[a,b,c],
C V e c t o r = [ a b c ] CVector=\begin{bmatrix} a \\ b \\ c \end{bmatrix} CVector=abc

通过指定行列数来获取行、列向量,更加方便快捷

>>> V=Matrix(1,3,[x,y,z])  #行向量,一行,V=[x  y  z]
>>> V=Matrix(3,1,[x,y,z])  #列向量,一列,V=[x  y  z].T
>>> M
Matrix([
[a, b, c],
[d, e, f]])
>>> M[0:M.rows*M.cols]  #组合成一行
[a, b, c, d, e, f]
>>> M[M.cols:M.cols*M.rows]  #取第二行
[d, e, f]

矩阵运算(Matrix Operations)

1、线代 (linear algebra) 核心是向量的线性运算

包括加+, 减-, 乘*(内积或点积 inner or dot product, v_1.T*v_2, v_1.dot(v_2)), 外积(outer product, v_1*v_2.T), 除/。

v_1, v_2 = Matrix([c,d]), Matrix([e,f])
M_1= a*v_1+b*v_2 # 线性加法
M_2 = v_1.T*v_2  # 点积, 结果是仅仅含有一个数的矩阵
v = v_1.dot(v_2) # 点积得到的结果是一个数值
u = v_1*v_2.T    # 外积得一个矩阵

M 1 = [ a c + b e a d + b f ] M_1=\begin{bmatrix} ac+be\\ ad+bf \end{bmatrix} M1=[ac+bead+bf] M 2 = [ c e + d f ] v = c e + d f u = [ c e c f d e d f ] \qquad M_2=[ce+df]\qquad v=ce+df\qquad u=\begin{bmatrix} ce & cf\\ de & df \end{bmatrix} M2=[ce+df]v=ce+dfu=[cedecfdf]

2、求偏导 M.diff(x)

V = Matrix([x,y,1]) #列向量,齐次坐标
M = A*V        #矩阵乘积
D = M.diff(x)  #对x求偏导

M = [ a x + b y + c d x + e y + f ] M=\begin{bmatrix} ax+by+c\\ dx+ey+f \end{bmatrix} M=[ax+by+cdx+ey+f] D = [ a d ] \qquad D=\begin{bmatrix} a\\ d \end{bmatrix} D=[ad]

3、逆矩阵 M**-1

>>> C=Matrix([[1,2],[3,4]])
>>> C**-1  #逆矩阵inverse
Matrix([
[-2,     1],
[3/2, -1/2]])

4、方阵求行列式的值 M.det()

>>> C.det()  #方阵的行列式求值
-2

5、添删矩阵的某行或某列

在某些情况下,需要对矩阵进行加上一行或者加上一列的操作,在这里就可以使用 row_insert 或者
col_insert 函数:第一个参数表示插入的位置,第二个参数就是相应的行向量或者列向量。

而在删除上就很简单了,直接使用 row_del 或者 col_del 即可.

>>> A.row_insert(1,Matrix([[10,10]]))  #第2行上插入
Matrix([
[ 1,  0],
[10, 10],
[ 0,  1]])
>>> A.col_insert(0,Matrix([3,5]))  #第1列上插入
Matrix([
[3, 1, 0],
[5, 0, 1]])
>>> A.row_del(0)  #删除第0+1行
>>> A
Matrix([[0, 1]])
>>> A.col_del(1)  #删除第1+1=2列
>>> A
Matrix([[0]])

6、叉积cross product

叉积采用 M.cross(A) 的方式实现

v_1, v_2 = Matrix([1,2,3]), Matrix([4,5,6])
v_3 = v_1.cross(v_2)
v_1.dot(v_3)  #0 因为 v_1和v_2都 垂直 v_3
v_2.dot(v_3)  #0

7、函数对矩阵元素的操作 M.applyfunc(myfunc)

f = lambda x: 2*x  #定义单变量函数
eye(3).applyfunc(f) #作用到矩阵的每个元素上

8、替换矩阵中的变量 M.subs(x,4)

M = eys(3)*x
M.subs(x,5) #将x用5代替
M.subs(x,y) #将x替换成y

矩阵属性(Matrix Properties)

SymPy提供了一个判断矩阵是否是带符号的矩阵的方法 .is_symbolic()

A.is_symbolic()  # 返回 True
C = Matrix[[1,2],[3,4]]
C.is_symbolic()  # 返回 False

创建特殊矩阵

  • 单位矩阵 eye(n,m)
    在矩阵论中,最常见的就是单位矩阵了,而单位矩阵只与一个参数有关,那就是矩阵的大小, Sympy中用函数 eye(n,m) 创建 n × m n\times m n×m的单位矩阵。
>>> eye(4)
Matrix([
[1, 0, 0, 0],
[0, 1, 0, 0],
[0, 0, 1, 0],
[0, 0, 0, 1]])
>>> eye(2,3)
Matrix([
[1, 0, 0],
[0, 1, 0]])
  • 零矩阵和全一矩阵 zeros(n,m), ones(n,m)
    另外还有全零 zeros(n,m)全一 ones(n,m) 矩阵,意思就是矩阵中的所有值全部是 零和一
>>> ones(3,4)
Matrix([
[1, 1, 1, 1],
[1, 1, 1, 1],
[1, 1, 1, 1]])
>>> zeros(3,2)
Matrix([
[0, 0],
[0, 0],
[0, 0]])
  • 对角矩阵 diag(n,m,k,...)
    而对角矩阵也可以使用 diag(n,m,k,...) 轻松获得:
>>> diag(1,2,3,4)
Matrix([
[1, 0, 0, 0],
[0, 2, 0, 0],
[0, 0, 3, 0],
[0, 0, 0, 4]])
  • 矩阵特征值、特征向量与对角化
    在对角化方面,同样可以使用 特征值eigenvals(),特征向量eigenvects(), 对角化diagonalize() 函数
>>> A=sympy.Matrix([[1,1],[0,2]])
>>> A
Matrix([
[1, 1],
[0, 2]])
>>> A.eigenvals()   # 特征值
{1: 1, 2: 1}
>>> A.eigenvects()  # 特征向量
[(1, 1, [Matrix([
[1],
[0]])]), (2, 1, [Matrix([
[1],
[1]])])]
>>> A.diagonalize()  # 对角化
(Matrix([
[1, 1],
[0, 1]]), Matrix([
[1, 0],
[0, 2]]))

>>> A=Matrix([[1,2],[2,2]])
>>> A.eigenvals()
{3/2 - sqrt(17)/2: 1, 3/2 + sqrt(17)/2: 1}
>>> A.eigenvects()
[(3/2 - sqrt(17)/2, 1, [Matrix([
[-2/(-1/2 + sqrt(17)/2)],
[                     1]])]), (3/2 + sqrt(17)/2, 1, [Matrix([
[-2/(-sqrt(17)/2 - 1/2)],
[                     1]])])]
>>> A.diagonalize()
(Matrix([
[-sqrt(17)/4 - 1/4, -1/4 + sqrt(17)/4],
[                1,                 1]]), Matrix([
[3/2 - sqrt(17)/2,                0],
[               0, 3/2 + sqrt(17)/2]]))

eigenvals() 返回的结果中,第一个表示特征值,第二个表示该特征值的重数。在特征向量 eigenvects()
中,第一个表示特征值,第二个表示特征值的重数,第三个表示特征向量。
在对角化 diagonalize() 中,第一个矩阵表示 P P P,第二个矩阵表示 D , A = P × D × P − 1 D, A=P\times D\times P^{-1} D,A=P×D×P1

  • 矩阵方程求解
    在矩阵中,最常见的还是多元一次方程的解。如果要求 A x = b Ax=b Ax=b 的解,可以有以下方案:
>>> A
Matrix([
[1, 1],
[0, 2]])
>>> b = sympy.Matrix([3,5])
>>> b
Matrix([
[3],
[5]])
>>> A**-1*b
Matrix([
[1/2],
[5/2]])
>>> sympy.linsolve((A,b))
FiniteSet((1/2, 5/2))
>>> sympy.linsolve((A,b),[x,y])
FiniteSet((1/2, 5/2))

创建符号矩阵的过程

def make_Aij(m, n, a='a') :
    from sympy import Symbol, Matrix # just in case they aren't already loaded
    A = zeros(m, n)
    for i in range(0, m) :
        for j in range(0, n) :
            s = a+'_'+str(i)+str(j)
            exec s + "= Symbol('" + s + "')" # go look up what "exec" does!
            exec "A[i, j] = " + s
    return A
C = make_Aij(2, 3, 'c')

创建矩阵 C = [ c 00 c 01 c 02 c 10 c 11 c 12 ] C=\begin{bmatrix} c_{00} & c_{01} & c_{02}\\ c_{10} & c_{11} & c_{12} \end{bmatrix} C=[c00c10c01c11c02c12]

这里的 exec 函数用来立刻生成符号(字符串)。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值