Как получить доступ к элементам матрицы Sympy для операций со строками? - PullRequest
0 голосов
/ 07 июня 2019

Я ищу способ доступа к элементам матрицы sympy для выполнения операций со строками, но, похоже, не могу найти способ сделать это или найти какую-либо существующую документацию, описывающую процесс.

Например, допустим, у меня есть следующий код:

import sympy as sp
from sympy import *

matrix = sp.Matrix([[3,2,2],[1,2,3]])

Я хочу разделить элемент в первой строке и втором столбце, в данном случае это 2. По-настоящему хакерский способ сделать так, чтобы я мог придумать, это сделать следующее:

a = int(matrix.row(0).col(2)[0])
matrix.row(0)/a

Но теперь первая строка моей матрицы

[3/2,1,1]

и я хочу снова разделить строку на 3/2, на этот раз мой предыдущий метод не работает. Как я могу выполнить эти операции со строками и как они могут обновить исходную матрицу? (т.е. когда я делю строку на 3, она обновляет строку в исходной матрице и не просто возвращает отдельную матрицу, отражающую только обновленную строку)

И есть ли какой-нибудь простой способ сделать перестановки строк / чередования (т. Е. R1 <-> r2) с матрицей sympy?

EDIT:

Я понял, что могу сделать часть деления своего вопроса, просто используя matrix[row#,:]/matrix[row#,column#], но я все еще не уверен, как эта операция строки должна быть непосредственно отражена в исходной матрице, или как сделать перестановку строк.

Ответы [ 2 ]

0 голосов
/ 08 июня 2019

Я все еще немного sympy новичок, но хорошо осведомлен в numpy. Итак, давайте посмотрим, будет ли sympy вести себя примерно так же.

В сеансе isympy:

In [67]: M = Matrix([[3,2,2],[1,2,3]])                                                                 

In [68]: M                                                                                             
Out[68]: 
⎡3  2  2⎤
⎢       ⎥
⎣1  2  3⎦

In [69]: M[0,:]             # a row, using a numpy style indexing                                                                                        
Out[69]: [3  2  2]

In [70]: M[0,1]             # an element                                                                           
Out[70]: 2

In [71]: M[0,:]/M[0,1]      # division, producing a new matrix                                                                            
Out[71]: [3/2  1  1]

In [72]: M                  # no change to M                                                                           
Out[72]: 
⎡3  2  2⎤
⎢       ⎥
⎣1  2  3⎦

In [73]: M[0,:]/=M[0,1]     # but with a /= (Python syntax)                                                                           

In [74]: M                                                                                             
Out[74]: 
⎡3/2  1  1⎤
⎢         ⎥
⎣ 1   2  3⎦

In [75]: M[0,:]/=3/2      # again                                                                             

In [76]: M                                                                                             
Out[76]: 
⎡1.0  0.666666666666667  0.666666666666667⎤
⎢                                         ⎥
⎣ 1           2                  3        ⎦

Это делило с плавающей запятой; Я подозреваю, что с другим делителем я мог бы сделать правильное дробное деление.

In [83]: M = Matrix([[3,2,2],[1,2,3]])                                                                 

In [84]: M[0,:]/=M[0,1]                                                                                

In [85]: M[0,:]/=Rational(3,2)                                                                         

In [86]: M                                                                                             
Out[86]: 
⎡1  2/3  2/3⎤
⎢           ⎥
⎣1   2    3 ⎦
0 голосов
/ 08 июня 2019

Когда у меня возникает вопрос, подобный этому, я пытаюсь найти справочник в справке:

>>> [w for w in dir(Matrix) if 'op' in w and not w.startswith('_')]
[col_op, copy, copyin_list, copyin_matrix, elementary_col_op, elementary_row_op, 
row_op, zip_row_op]

>>> help(Matrix.row_op)
Help on method row_op in module sympy.matrices.dense:

row_op(self, i, f) unbound sympy.matrices.dense.MutableDenseMatrix method
    In-place operation on row ``i`` using two-arg functor whose args are
    interpreted as ``(self[i, j], j)``.
...

>>> help(Matrix.elementary_row_op)
Help on method elementary_row_op in module sympy.matrices.matrices:

elementary_row_op(self, op='n->kn', row=None, k=None, row1=None, row2=None) unbound 
sympy.matrices.dense.MutableDenseMatrix method
    Performs the elementary row operation `op`.

    `op` may be one of

        * "n->kn" (row n goes to k*n)
        * "n<->m" (swap row n and row m)
        * "n->n+km" (row n goes to row n + k*row m)

    Parameters
    ==========

    op : string; the elementary row operation
    row : the row to apply the row operation
    k : the multiple to apply in the row operation
    row1 : one row of a row swap
    row2 : second row of a row swap or row "m" in the row operation
           "n->n+km"

Похоже, можно использовать любой из них.

>>> m =  Matrix([[3,2,2],[1,2,3]])
>>> m.row_op(0, lambda x, j: x/2)
>>> m
Matrix([
[3/2, 1, 1],
[  1, 2, 3]])
>>> m.row_op(0, lambda x, j: x/(3/2))
>>> m
Matrix([
[1, 2/3, 2/3],
[1,   2,   3]])

или

>>> m =  Matrix([[3,2,2],[1,2,3]])
>>> m.elementary_row_op('n->kn',row1=0,k=1/3)
Matrix([
[1, 2/3, 2/3],
[1,   2,   3]])
...