determinant.py 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141
  1. from sympy.core.basic import Basic
  2. from sympy.core.expr import Expr
  3. from sympy.core.singleton import S
  4. from sympy.core.sympify import sympify
  5. from sympy.matrices.common import NonSquareMatrixError
  6. class Determinant(Expr):
  7. """Matrix Determinant
  8. Represents the determinant of a matrix expression.
  9. Examples
  10. ========
  11. >>> from sympy import MatrixSymbol, Determinant, eye
  12. >>> A = MatrixSymbol('A', 3, 3)
  13. >>> Determinant(A)
  14. Determinant(A)
  15. >>> Determinant(eye(3)).doit()
  16. 1
  17. """
  18. is_commutative = True
  19. def __new__(cls, mat):
  20. mat = sympify(mat)
  21. if not mat.is_Matrix:
  22. raise TypeError("Input to Determinant, %s, not a matrix" % str(mat))
  23. if not mat.is_square:
  24. raise NonSquareMatrixError("Det of a non-square matrix")
  25. return Basic.__new__(cls, mat)
  26. @property
  27. def arg(self):
  28. return self.args[0]
  29. @property
  30. def kind(self):
  31. return self.arg.kind.element_kind
  32. def doit(self, expand=False):
  33. try:
  34. return self.arg._eval_determinant()
  35. except (AttributeError, NotImplementedError):
  36. return self
  37. def det(matexpr):
  38. """ Matrix Determinant
  39. Examples
  40. ========
  41. >>> from sympy import MatrixSymbol, det, eye
  42. >>> A = MatrixSymbol('A', 3, 3)
  43. >>> det(A)
  44. Determinant(A)
  45. >>> det(eye(3))
  46. 1
  47. """
  48. return Determinant(matexpr).doit()
  49. class Permanent(Expr):
  50. """Matrix Permanent
  51. Represents the permanent of a matrix expression.
  52. Examples
  53. ========
  54. >>> from sympy import MatrixSymbol, Permanent, ones
  55. >>> A = MatrixSymbol('A', 3, 3)
  56. >>> Permanent(A)
  57. Permanent(A)
  58. >>> Permanent(ones(3, 3)).doit()
  59. 6
  60. """
  61. def __new__(cls, mat):
  62. mat = sympify(mat)
  63. if not mat.is_Matrix:
  64. raise TypeError("Input to Permanent, %s, not a matrix" % str(mat))
  65. return Basic.__new__(cls, mat)
  66. @property
  67. def arg(self):
  68. return self.args[0]
  69. def doit(self, expand=False):
  70. try:
  71. return self.arg.per()
  72. except (AttributeError, NotImplementedError):
  73. return self
  74. def per(matexpr):
  75. """ Matrix Permanent
  76. Examples
  77. ========
  78. >>> from sympy import MatrixSymbol, Matrix, per, ones
  79. >>> A = MatrixSymbol('A', 3, 3)
  80. >>> per(A)
  81. Permanent(A)
  82. >>> per(ones(5, 5))
  83. 120
  84. >>> M = Matrix([1, 2, 5])
  85. >>> per(M)
  86. 8
  87. """
  88. return Permanent(matexpr).doit()
  89. from sympy.assumptions.ask import ask, Q
  90. from sympy.assumptions.refine import handlers_dict
  91. def refine_Determinant(expr, assumptions):
  92. """
  93. >>> from sympy import MatrixSymbol, Q, assuming, refine, det
  94. >>> X = MatrixSymbol('X', 2, 2)
  95. >>> det(X)
  96. Determinant(X)
  97. >>> with assuming(Q.orthogonal(X)):
  98. ... print(refine(det(X)))
  99. 1
  100. """
  101. if ask(Q.orthogonal(expr.arg), assumptions):
  102. return S.One
  103. elif ask(Q.singular(expr.arg), assumptions):
  104. return S.Zero
  105. elif ask(Q.unit_triangular(expr.arg), assumptions):
  106. return S.One
  107. return expr
  108. handlers_dict['Determinant'] = refine_Determinant