Coverage for /usr/lib/python3/dist-packages/sympy/matrices/expressions/inverse.py: 39%
51 statements
« prev ^ index » next coverage.py v7.9.1, created at 2025-06-14 15:55 +0200
« prev ^ index » next coverage.py v7.9.1, created at 2025-06-14 15:55 +0200
1from sympy.core.sympify import _sympify
2from sympy.core import S, Basic
4from sympy.matrices.common import NonSquareMatrixError
5from sympy.matrices.expressions.matpow import MatPow
8class Inverse(MatPow):
9 """
10 The multiplicative inverse of a matrix expression
12 This is a symbolic object that simply stores its argument without
13 evaluating it. To actually compute the inverse, use the ``.inverse()``
14 method of matrices.
16 Examples
17 ========
19 >>> from sympy import MatrixSymbol, Inverse
20 >>> A = MatrixSymbol('A', 3, 3)
21 >>> B = MatrixSymbol('B', 3, 3)
22 >>> Inverse(A)
23 A**(-1)
24 >>> A.inverse() == Inverse(A)
25 True
26 >>> (A*B).inverse()
27 B**(-1)*A**(-1)
28 >>> Inverse(A*B)
29 (A*B)**(-1)
31 """
32 is_Inverse = True
33 exp = S.NegativeOne
35 def __new__(cls, mat, exp=S.NegativeOne):
36 # exp is there to make it consistent with
37 # inverse.func(*inverse.args) == inverse
38 mat = _sympify(mat)
39 exp = _sympify(exp)
40 if not mat.is_Matrix:
41 raise TypeError("mat should be a matrix")
42 if mat.is_square is False:
43 raise NonSquareMatrixError("Inverse of non-square matrix %s" % mat)
44 return Basic.__new__(cls, mat, exp)
46 @property
47 def arg(self):
48 return self.args[0]
50 @property
51 def shape(self):
52 return self.arg.shape
54 def _eval_inverse(self):
55 return self.arg
57 def _eval_determinant(self):
58 from sympy.matrices.expressions.determinant import det
59 return 1/det(self.arg)
61 def doit(self, **hints):
62 if 'inv_expand' in hints and hints['inv_expand'] == False:
63 return self
65 arg = self.arg
66 if hints.get('deep', True):
67 arg = arg.doit(**hints)
69 return arg.inverse()
71 def _eval_derivative_matrix_lines(self, x):
72 arg = self.args[0]
73 lines = arg._eval_derivative_matrix_lines(x)
74 for line in lines:
75 line.first_pointer *= -self.T
76 line.second_pointer *= self
77 return lines
80from sympy.assumptions.ask import ask, Q
81from sympy.assumptions.refine import handlers_dict
84def refine_Inverse(expr, assumptions):
85 """
86 >>> from sympy import MatrixSymbol, Q, assuming, refine
87 >>> X = MatrixSymbol('X', 2, 2)
88 >>> X.I
89 X**(-1)
90 >>> with assuming(Q.orthogonal(X)):
91 ... print(refine(X.I))
92 X.T
93 """
94 if ask(Q.orthogonal(expr), assumptions):
95 return expr.arg.T
96 elif ask(Q.unitary(expr), assumptions):
97 return expr.arg.conjugate()
98 elif ask(Q.singular(expr), assumptions):
99 raise ValueError("Inverse of singular matrix %s" % expr.arg)
101 return expr
103handlers_dict['Inverse'] = refine_Inverse