Base class for matrices, part 0¶
Note
For design documentation see matrix/docs.py.
EXAMPLES:
sage: matrix(2, [1,2,3,4])
[1 2]
[3 4]
>>> from sage.all import *
>>> matrix(Integer(2), [Integer(1),Integer(2),Integer(3),Integer(4)])
[1 2]
[3 4]
- class sage.matrix.matrix0.Matrix[source]¶
Bases:
Matrix
A generic matrix.
The
Matrix
class is the base class for all matrix classes. To create aMatrix
, first create aMatrixSpace
, then coerce a list of elements into theMatrixSpace
. See the documentation ofMatrixSpace
for more details.EXAMPLES:
We illustrate matrices and matrix spaces. Note that no actual matrix that you make should have class Matrix; the class should always be derived from Matrix.
sage: M = MatrixSpace(CDF,2,3); M Full MatrixSpace of 2 by 3 dense matrices over Complex Double Field sage: a = M([1,2,3, 4,5,6]); a [1.0 2.0 3.0] [4.0 5.0 6.0] sage: type(a) <class 'sage.matrix.matrix_complex_double_dense.Matrix_complex_double_dense'> sage: parent(a) Full MatrixSpace of 2 by 3 dense matrices over Complex Double Field
>>> from sage.all import * >>> M = MatrixSpace(CDF,Integer(2),Integer(3)); M Full MatrixSpace of 2 by 3 dense matrices over Complex Double Field >>> a = M([Integer(1),Integer(2),Integer(3), Integer(4),Integer(5),Integer(6)]); a [1.0 2.0 3.0] [4.0 5.0 6.0] >>> type(a) <class 'sage.matrix.matrix_complex_double_dense.Matrix_complex_double_dense'> >>> parent(a) Full MatrixSpace of 2 by 3 dense matrices over Complex Double Field
sage: matrix(CDF, 2,3, [1,2,3, 4,5,6]) [1.0 2.0 3.0] [4.0 5.0 6.0] sage: Mat(CDF,2,3)(range(1,7)) [1.0 2.0 3.0] [4.0 5.0 6.0]
>>> from sage.all import * >>> matrix(CDF, Integer(2),Integer(3), [Integer(1),Integer(2),Integer(3), Integer(4),Integer(5),Integer(6)]) [1.0 2.0 3.0] [4.0 5.0 6.0] >>> Mat(CDF,Integer(2),Integer(3))(range(Integer(1),Integer(7))) [1.0 2.0 3.0] [4.0 5.0 6.0]
sage: Q.<i,j,k> = QuaternionAlgebra(QQ, -1,-1) sage: matrix(Q,2,1,[1,2]) [1] [2]
>>> from sage.all import * >>> Q = QuaternionAlgebra(QQ, -Integer(1),-Integer(1), names=('i', 'j', 'k',)); (i, j, k,) = Q._first_ngens(3) >>> matrix(Q,Integer(2),Integer(1),[Integer(1),Integer(2)]) [1] [2]
- act_on_polynomial(f)[source]¶
Return the polynomial
f(self*x)
.INPUT:
self
– an nxn matrixf
– a polynomial in n variables x=(x1,…,xn)
EXAMPLES:
sage: R.<x,y> = QQ[] sage: x, y = R.gens() sage: f = x**2 - y**2 sage: M = MatrixSpace(QQ, 2) sage: A = M([1,2,3,4]) sage: A.act_on_polynomial(f) -8*x^2 - 20*x*y - 12*y^2
>>> from sage.all import * >>> R = QQ['x, y']; (x, y,) = R._first_ngens(2) >>> x, y = R.gens() >>> f = x**Integer(2) - y**Integer(2) >>> M = MatrixSpace(QQ, Integer(2)) >>> A = M([Integer(1),Integer(2),Integer(3),Integer(4)]) >>> A.act_on_polynomial(f) -8*x^2 - 20*x*y - 12*y^2
- add_multiple_of_column(i, j, s, start_row=0)[source]¶
Add s times column j to column i.
EXAMPLES: We add -1 times the third column to the second column of an integer matrix, remembering to start numbering cols at zero:
sage: a = matrix(ZZ,2,3,range(6)); a [0 1 2] [3 4 5] sage: a.add_multiple_of_column(1,2,-1) sage: a [ 0 -1 2] [ 3 -1 5]
>>> from sage.all import * >>> a = matrix(ZZ,Integer(2),Integer(3),range(Integer(6))); a [0 1 2] [3 4 5] >>> a.add_multiple_of_column(Integer(1),Integer(2),-Integer(1)) >>> a [ 0 -1 2] [ 3 -1 5]
To add a rational multiple, we first need to change the base ring:
sage: a = a.change_ring(QQ) sage: a.add_multiple_of_column(1,0,1/3) sage: a [ 0 -1 2] [ 3 0 5]
>>> from sage.all import * >>> a = a.change_ring(QQ) >>> a.add_multiple_of_column(Integer(1),Integer(0),Integer(1)/Integer(3)) >>> a [ 0 -1 2] [ 3 0 5]
If not, we get an error message:
sage: a.add_multiple_of_column(1, 0, SR.I()) # needs sage.symbolic Traceback (most recent call last): ... TypeError: Multiplying column by Symbolic Ring element cannot be done over Rational Field, use change_ring or with_added_multiple_of_column instead.
>>> from sage.all import * >>> a.add_multiple_of_column(Integer(1), Integer(0), SR.I()) # needs sage.symbolic Traceback (most recent call last): ... TypeError: Multiplying column by Symbolic Ring element cannot be done over Rational Field, use change_ring or with_added_multiple_of_column instead.
- add_multiple_of_row(i, j, s, start_col=0)[source]¶
Add s times row j to row i.
EXAMPLES: We add -3 times the first row to the second row of an integer matrix, remembering to start numbering rows at zero:
sage: a = matrix(ZZ,2,3,range(6)); a [0 1 2] [3 4 5] sage: a.add_multiple_of_row(1,0,-3) sage: a [ 0 1 2] [ 3 1 -1]
>>> from sage.all import * >>> a = matrix(ZZ,Integer(2),Integer(3),range(Integer(6))); a [0 1 2] [3 4 5] >>> a.add_multiple_of_row(Integer(1),Integer(0),-Integer(3)) >>> a [ 0 1 2] [ 3 1 -1]
To add a rational multiple, we first need to change the base ring:
sage: a = a.change_ring(QQ) sage: a.add_multiple_of_row(1,0,1/3) sage: a [ 0 1 2] [ 3 4/3 -1/3]
>>> from sage.all import * >>> a = a.change_ring(QQ) >>> a.add_multiple_of_row(Integer(1),Integer(0),Integer(1)/Integer(3)) >>> a [ 0 1 2] [ 3 4/3 -1/3]
If not, we get an error message:
sage: a.add_multiple_of_row(1, 0, SR.I()) # needs sage.symbolic Traceback (most recent call last): ... TypeError: Multiplying row by Symbolic Ring element cannot be done over Rational Field, use change_ring or with_added_multiple_of_row instead.
>>> from sage.all import * >>> a.add_multiple_of_row(Integer(1), Integer(0), SR.I()) # needs sage.symbolic Traceback (most recent call last): ... TypeError: Multiplying row by Symbolic Ring element cannot be done over Rational Field, use change_ring or with_added_multiple_of_row instead.
- add_to_entry(i, j, elt)[source]¶
Add
elt
to the entry at position(i, j)
.EXAMPLES:
sage: m = matrix(QQ['x,y'], 2, 2) sage: m.add_to_entry(0, 1, 2) sage: m [0 2] [0 0]
>>> from sage.all import * >>> m = matrix(QQ['x,y'], Integer(2), Integer(2)) >>> m.add_to_entry(Integer(0), Integer(1), Integer(2)) >>> m [0 2] [0 0]
- anticommutator(other)[source]¶
Return the anticommutator
self
andother
.The anticommutator of two \(n \times n\) matrices \(A\) and \(B\) is defined as \(\{A, B\} := AB + BA\) (sometimes this is written as \([A, B]_+\)).
EXAMPLES:
sage: A = Matrix(ZZ, 2, 2, range(4)) sage: B = Matrix(ZZ, 2, 2, [0, 1, 0, 0]) sage: A.anticommutator(B) [2 3] [0 2] sage: A.anticommutator(B) == B.anticommutator(A) True sage: A.commutator(B) + B.anticommutator(A) == 2*A*B True
>>> from sage.all import * >>> A = Matrix(ZZ, Integer(2), Integer(2), range(Integer(4))) >>> B = Matrix(ZZ, Integer(2), Integer(2), [Integer(0), Integer(1), Integer(0), Integer(0)]) >>> A.anticommutator(B) [2 3] [0 2] >>> A.anticommutator(B) == B.anticommutator(A) True >>> A.commutator(B) + B.anticommutator(A) == Integer(2)*A*B True
- base_ring()[source]¶
Return the base ring of the matrix.
EXAMPLES:
sage: m = matrix(QQ, 2, [1,2,3,4]) sage: m.base_ring() Rational Field
>>> from sage.all import * >>> m = matrix(QQ, Integer(2), [Integer(1),Integer(2),Integer(3),Integer(4)]) >>> m.base_ring() Rational Field
- change_ring(ring)[source]¶
Return the matrix obtained by coercing the entries of this matrix into the given ring.
Always returns a copy (unless
self
is immutable, in which case returnsself
).EXAMPLES:
sage: A = Matrix(QQ, 2, 2, [1/2, 1/3, 1/3, 1/4]) sage: A.parent() Full MatrixSpace of 2 by 2 dense matrices over Rational Field sage: A.change_ring(GF(25,'a')) # needs sage.rings.finite_rings [3 2] [2 4] sage: A.change_ring(GF(25,'a')).parent() # needs sage.rings.finite_rings Full MatrixSpace of 2 by 2 dense matrices over Finite Field in a of size 5^2 sage: A.change_ring(ZZ) # needs sage.rings.finite_rings Traceback (most recent call last): ... TypeError: matrix has denominators so can...t change to ZZ
>>> from sage.all import * >>> A = Matrix(QQ, Integer(2), Integer(2), [Integer(1)/Integer(2), Integer(1)/Integer(3), Integer(1)/Integer(3), Integer(1)/Integer(4)]) >>> A.parent() Full MatrixSpace of 2 by 2 dense matrices over Rational Field >>> A.change_ring(GF(Integer(25),'a')) # needs sage.rings.finite_rings [3 2] [2 4] >>> A.change_ring(GF(Integer(25),'a')).parent() # needs sage.rings.finite_rings Full MatrixSpace of 2 by 2 dense matrices over Finite Field in a of size 5^2 >>> A.change_ring(ZZ) # needs sage.rings.finite_rings Traceback (most recent call last): ... TypeError: matrix has denominators so can...t change to ZZ
Changing rings preserves subdivisions:
sage: A.subdivide([1], []); A [1/2 1/3] [-------] [1/3 1/4] sage: A.change_ring(GF(25,'a')) # needs sage.rings.finite_rings [3 2] [---] [2 4]
>>> from sage.all import * >>> A.subdivide([Integer(1)], []); A [1/2 1/3] [-------] [1/3 1/4] >>> A.change_ring(GF(Integer(25),'a')) # needs sage.rings.finite_rings [3 2] [---] [2 4]
- commutator(other)[source]¶
Return the commutator self*other - other*self.
EXAMPLES:
sage: A = Matrix(ZZ, 2, 2, range(4)) sage: B = Matrix(ZZ, 2, 2, [0, 1, 0, 0]) sage: A.commutator(B) [-2 -3] [ 0 2] sage: A.commutator(B) == -B.commutator(A) True
>>> from sage.all import * >>> A = Matrix(ZZ, Integer(2), Integer(2), range(Integer(4))) >>> B = Matrix(ZZ, Integer(2), Integer(2), [Integer(0), Integer(1), Integer(0), Integer(0)]) >>> A.commutator(B) [-2 -3] [ 0 2] >>> A.commutator(B) == -B.commutator(A) True
- dense_coefficient_list(order=None)[source]¶
Return a list of all coefficients of
self
.By default, this is the same as
list()
.INPUT:
order
– (optional) an ordering of the basis indexing set
EXAMPLES:
sage: A = matrix([[1,2,3], [4,5,6]]) sage: A.dense_coefficient_list() [1, 2, 3, 4, 5, 6] sage: A.dense_coefficient_list([(1,2), (1,0), (0,1), (0,2), (0,0), (1,1)]) [6, 4, 2, 3, 1, 5]
>>> from sage.all import * >>> A = matrix([[Integer(1),Integer(2),Integer(3)], [Integer(4),Integer(5),Integer(6)]]) >>> A.dense_coefficient_list() [1, 2, 3, 4, 5, 6] >>> A.dense_coefficient_list([(Integer(1),Integer(2)), (Integer(1),Integer(0)), (Integer(0),Integer(1)), (Integer(0),Integer(2)), (Integer(0),Integer(0)), (Integer(1),Integer(1))]) [6, 4, 2, 3, 1, 5]
- dict(copy=True)[source]¶
Dictionary of the elements of
self
with keys pairs(i,j)
and values the nonzero entries ofself
.INPUT:
copy
– boolean (default:True
); make a copy of thedict
corresponding toself
If
copy=True
, then is safe to change the returned dictionary. Otherwise, this can cause undesired behavior by mutating thedict
.EXAMPLES:
sage: R.<x,y> = QQ[] sage: a = matrix(R,2,[x,y,0, 0,0,2*x+y]); a [ x y 0] [ 0 0 2*x + y] sage: d = a.dict(); d {(0, 0): x, (0, 1): y, (1, 2): 2*x + y}
>>> from sage.all import * >>> R = QQ['x, y']; (x, y,) = R._first_ngens(2) >>> a = matrix(R,Integer(2),[x,y,Integer(0), Integer(0),Integer(0),Integer(2)*x+y]); a [ x y 0] [ 0 0 2*x + y] >>> d = a.dict(); d {(0, 0): x, (0, 1): y, (1, 2): 2*x + y}
Notice that changing the returned list does not change a (the list is a copy):
sage: d[0,0] = 25 sage: a [ x y 0] [ 0 0 2*x + y]
>>> from sage.all import * >>> d[Integer(0),Integer(0)] = Integer(25) >>> a [ x y 0] [ 0 0 2*x + y]
- dimensions()[source]¶
Return the dimensions of this matrix as the tuple (nrows, ncols).
EXAMPLES:
sage: M = matrix([[1,2,3],[4,5,6]]) sage: N = M.transpose() sage: M.dimensions() (2, 3) sage: N.dimensions() (3, 2)
>>> from sage.all import * >>> M = matrix([[Integer(1),Integer(2),Integer(3)],[Integer(4),Integer(5),Integer(6)]]) >>> N = M.transpose() >>> M.dimensions() (2, 3) >>> N.dimensions() (3, 2)
AUTHORS:
Benjamin Lundell (2012-02-09): examples
- inverse_of_unit(algorithm=None)[source]¶
Return the inverse of this matrix in the same matrix space.
The matrix must be invertible on the base ring. Otherwise, an
ArithmeticError
is raised.The computation goes through the matrix of cofactors and avoids division. In particular the base ring does not need to have a fraction field.
INPUT:
algorithm
– (default:None
) eitherNone
or'df'
(for division free)
EXAMPLES:
sage: R.<a,b,c,d> = ZZ[] sage: RR = R.quotient(a*d - b*c - 1) sage: a,b,c,d = RR.gens() # needs sage.libs.singular sage: m = matrix(2, [a,b, c,d]) sage: n = m.inverse_of_unit() # needs sage.libs.singular sage: m * n # needs sage.libs.singular [1 0] [0 1] sage: matrix(RR, 2, 1, [a,b]).inverse_of_unit() # needs sage.libs.singular Traceback (most recent call last): ... ArithmeticError: self must be a square matrix sage: matrix(RR, 1, 1, [2]).inverse_of_unit() # needs sage.libs.singular Traceback (most recent call last): ... ArithmeticError: non-invertible matrix sage: R = ZZ.cartesian_product(ZZ) sage: m = matrix(R, 2, [R((2,1)), R((1,1)), R((1,1)), R((1,2))]) sage: m * m.inverse_of_unit() [(1, 1) (0, 0)] [(0, 0) (1, 1)]
>>> from sage.all import * >>> R = ZZ['a, b, c, d']; (a, b, c, d,) = R._first_ngens(4) >>> RR = R.quotient(a*d - b*c - Integer(1)) >>> a,b,c,d = RR.gens() # needs sage.libs.singular >>> m = matrix(Integer(2), [a,b, c,d]) >>> n = m.inverse_of_unit() # needs sage.libs.singular >>> m * n # needs sage.libs.singular [1 0] [0 1] >>> matrix(RR, Integer(2), Integer(1), [a,b]).inverse_of_unit() # needs sage.libs.singular Traceback (most recent call last): ... ArithmeticError: self must be a square matrix >>> matrix(RR, Integer(1), Integer(1), [Integer(2)]).inverse_of_unit() # needs sage.libs.singular Traceback (most recent call last): ... ArithmeticError: non-invertible matrix >>> R = ZZ.cartesian_product(ZZ) >>> m = matrix(R, Integer(2), [R((Integer(2),Integer(1))), R((Integer(1),Integer(1))), R((Integer(1),Integer(1))), R((Integer(1),Integer(2)))]) >>> m * m.inverse_of_unit() [(1, 1) (0, 0)] [(0, 0) (1, 1)]
Tests for Issue #28570:
sage: P = posets.TamariLattice(7) # needs sage.graphs sage: M = P._hasse_diagram._leq_matrix # needs sage.graphs sage: M.inverse_of_unit() # this was very slow, now 1s # needs sage.graphs 429 x 429 sparse matrix over Integer Ring... sage: m = matrix(Zmod(2**2), 1, 1, [1], sparse=True) sage: mi = ~m; mi [1] sage: mi.parent() Full MatrixSpace of 1 by 1 sparse matrices over Ring of integers modulo 4
>>> from sage.all import * >>> P = posets.TamariLattice(Integer(7)) # needs sage.graphs >>> M = P._hasse_diagram._leq_matrix # needs sage.graphs >>> M.inverse_of_unit() # this was very slow, now 1s # needs sage.graphs 429 x 429 sparse matrix over Integer Ring... >>> m = matrix(Zmod(Integer(2)**Integer(2)), Integer(1), Integer(1), [Integer(1)], sparse=True) >>> mi = ~m; mi [1] >>> mi.parent() Full MatrixSpace of 1 by 1 sparse matrices over Ring of integers modulo 4
- is_alternating()[source]¶
Return
True
ifself
is an alternating matrix.Here, “alternating matrix” means a square matrix \(A\) satisfying \(A^T = -A\) and such that the diagonal entries of \(A\) are \(0\). Notice that the condition that the diagonal entries be \(0\) is not redundant for matrices over arbitrary ground rings (but it is redundant when \(2\) is invertible in the ground ring). A square matrix \(A\) only required to satisfy \(A^T = -A\) is said to be “skew-symmetric”, and this property is checked by the
is_skew_symmetric()
method.EXAMPLES:
sage: m = matrix(QQ, [[0,2], [-2,0]]) sage: m.is_alternating() True sage: m = matrix(QQ, [[1,2], [2,1]]) sage: m.is_alternating() False
>>> from sage.all import * >>> m = matrix(QQ, [[Integer(0),Integer(2)], [-Integer(2),Integer(0)]]) >>> m.is_alternating() True >>> m = matrix(QQ, [[Integer(1),Integer(2)], [Integer(2),Integer(1)]]) >>> m.is_alternating() False
In contrast to the property of being skew-symmetric, the property of being alternating does not tolerate nonzero entries on the diagonal even if they are their own negatives:
sage: n = matrix(Zmod(4), [[0, 1], [-1, 2]]) sage: n.is_alternating() False
>>> from sage.all import * >>> n = matrix(Zmod(Integer(4)), [[Integer(0), Integer(1)], [-Integer(1), Integer(2)]]) >>> n.is_alternating() False
- is_dense()[source]¶
Return
True
if this is a dense matrix.In Sage, being dense is a property of the underlying representation, not the number of nonzero entries.
EXAMPLES:
sage: matrix(QQ, 2, 2, range(4)).is_dense() True sage: matrix(QQ, 2, 2, range(4), sparse=True).is_dense() False
>>> from sage.all import * >>> matrix(QQ, Integer(2), Integer(2), range(Integer(4))).is_dense() True >>> matrix(QQ, Integer(2), Integer(2), range(Integer(4)), sparse=True).is_dense() False
- is_hermitian()[source]¶
Return
True
if the matrix is equal to its conjugate-transpose.OUTPUT:
True
if the matrix is square and equal to the transpose with every entry conjugated, andFalse
otherwise.Note that if conjugation has no effect on elements of the base ring (such as for integers), then the
is_symmetric()
method is equivalent and faster.This routine is for matrices over exact rings and so may not work properly for matrices over
RR
orCC
. For matrices with approximate entries, the rings of double-precision floating-point numbers,RDF
andCDF
, are a better choice since thesage.matrix.matrix_double_dense.Matrix_double_dense.is_hermitian()
method has a tolerance parameter. This provides control over allowing for minor discrepancies between entries when checking equality.The result is cached.
EXAMPLES:
sage: # needs sage.rings.number_field sage: A = matrix(QQbar, [[ 1 + I, 1 - 6*I, -1 - I], ....: [-3 - I, -4*I, -2], ....: [-1 + I, -2 - 8*I, 2 + I]]) sage: A.is_hermitian() False sage: B = A * A.conjugate_transpose() sage: B.is_hermitian() True
>>> from sage.all import * >>> # needs sage.rings.number_field >>> A = matrix(QQbar, [[ Integer(1) + I, Integer(1) - Integer(6)*I, -Integer(1) - I], ... [-Integer(3) - I, -Integer(4)*I, -Integer(2)], ... [-Integer(1) + I, -Integer(2) - Integer(8)*I, Integer(2) + I]]) >>> A.is_hermitian() False >>> B = A * A.conjugate_transpose() >>> B.is_hermitian() True
Sage has several fields besides the entire complex numbers where conjugation is non-trivial.
sage: # needs sage.rings.number_field sage: F.<b> = QuadraticField(-7) sage: C = matrix(F, [[-2*b - 3, 7*b - 6, -b + 3], ....: [-2*b - 3, -3*b + 2, -2*b], ....: [ b + 1, 0, -2]]) sage: C.is_hermitian() False sage: C = C*C.conjugate_transpose() sage: C.is_hermitian() True
>>> from sage.all import * >>> # needs sage.rings.number_field >>> F = QuadraticField(-Integer(7), names=('b',)); (b,) = F._first_ngens(1) >>> C = matrix(F, [[-Integer(2)*b - Integer(3), Integer(7)*b - Integer(6), -b + Integer(3)], ... [-Integer(2)*b - Integer(3), -Integer(3)*b + Integer(2), -Integer(2)*b], ... [ b + Integer(1), Integer(0), -Integer(2)]]) >>> C.is_hermitian() False >>> C = C*C.conjugate_transpose() >>> C.is_hermitian() True
A matrix that is nearly Hermitian, but for a non-real diagonal entry.
sage: # needs sage.rings.number_field sage: A = matrix(QQbar, [[ 2, 2-I, 1+4*I], ....: [ 2+I, 3+I, 2-6*I], ....: [1-4*I, 2+6*I, 5]]) sage: A.is_hermitian() False sage: A[1, 1] = 132 sage: A.is_hermitian() True
>>> from sage.all import * >>> # needs sage.rings.number_field >>> A = matrix(QQbar, [[ Integer(2), Integer(2)-I, Integer(1)+Integer(4)*I], ... [ Integer(2)+I, Integer(3)+I, Integer(2)-Integer(6)*I], ... [Integer(1)-Integer(4)*I, Integer(2)+Integer(6)*I, Integer(5)]]) >>> A.is_hermitian() False >>> A[Integer(1), Integer(1)] = Integer(132) >>> A.is_hermitian() True
Rectangular matrices are never Hermitian.
sage: A = matrix(QQbar, 3, 4) # needs sage.rings.number_field sage: A.is_hermitian() # needs sage.rings.number_field False
>>> from sage.all import * >>> A = matrix(QQbar, Integer(3), Integer(4)) # needs sage.rings.number_field >>> A.is_hermitian() # needs sage.rings.number_field False
A square, empty matrix is trivially Hermitian.
sage: A = matrix(QQ, 0, 0) sage: A.is_hermitian() True
>>> from sage.all import * >>> A = matrix(QQ, Integer(0), Integer(0)) >>> A.is_hermitian() True
- is_immutable()[source]¶
Return
True
if this matrix is immutable.See the documentation for self.set_immutable for more details about mutability.
EXAMPLES:
sage: A = Matrix(QQ['t','s'], 2, 2, range(4)) sage: A.is_immutable() False sage: A.set_immutable() sage: A.is_immutable() True
>>> from sage.all import * >>> A = Matrix(QQ['t','s'], Integer(2), Integer(2), range(Integer(4))) >>> A.is_immutable() False >>> A.set_immutable() >>> A.is_immutable() True
- is_invertible()[source]¶
Return
True
if this matrix is invertible.EXAMPLES: The following matrix is invertible over \(\QQ\) but not over \(\ZZ\).
sage: A = MatrixSpace(ZZ, 2)(range(4)) sage: A.is_invertible() False sage: A.matrix_over_field().is_invertible() True
>>> from sage.all import * >>> A = MatrixSpace(ZZ, Integer(2))(range(Integer(4))) >>> A.is_invertible() False >>> A.matrix_over_field().is_invertible() True
The inverse function is a constructor for matrices over the fraction field, so it can work even if A is not invertible.
sage: ~A # inverse of A [-3/2 1/2] [ 1 0]
>>> from sage.all import * >>> ~A # inverse of A [-3/2 1/2] [ 1 0]
The next matrix is invertible over \(\ZZ\).
sage: A = MatrixSpace(IntegerRing(), 2)([1,10,0,-1]) sage: A.is_invertible() True sage: ~A # compute the inverse [ 1 10] [ 0 -1]
>>> from sage.all import * >>> A = MatrixSpace(IntegerRing(), Integer(2))([Integer(1),Integer(10),Integer(0),-Integer(1)]) >>> A.is_invertible() True >>> ~A # compute the inverse [ 1 10] [ 0 -1]
The following nontrivial matrix is invertible over \(\ZZ[x]\).
sage: R.<x> = PolynomialRing(IntegerRing()) sage: A = MatrixSpace(R, 2)([1,x,0,-1]) sage: A.is_invertible() True sage: ~A [ 1 x] [ 0 -1]
>>> from sage.all import * >>> R = PolynomialRing(IntegerRing(), names=('x',)); (x,) = R._first_ngens(1) >>> A = MatrixSpace(R, Integer(2))([Integer(1),x,Integer(0),-Integer(1)]) >>> A.is_invertible() True >>> ~A [ 1 x] [ 0 -1]
- is_mutable()[source]¶
Return
True
if this matrix is mutable.See the documentation for self.set_immutable for more details about mutability.
EXAMPLES:
sage: A = Matrix(QQ['t','s'], 2, 2, range(4)) sage: A.is_mutable() True sage: A.set_immutable() sage: A.is_mutable() False
>>> from sage.all import * >>> A = Matrix(QQ['t','s'], Integer(2), Integer(2), range(Integer(4))) >>> A.is_mutable() True >>> A.set_immutable() >>> A.is_mutable() False
- is_singular()[source]¶
Return
True
ifself
is singular.OUTPUT:
A square matrix is singular if it has a zero determinant and this method will return
True
in exactly this case. When the entries of the matrix come from a field, this is equivalent to having a nontrivial kernel, or lacking an inverse, or having linearly dependent rows, or having linearly dependent columns.For square matrices over a field the methods
is_invertible()
andis_singular()
are logical opposites. However, it is an error to applyis_singular()
to a matrix that is not square, whileis_invertible()
will always returnFalse
for a matrix that is not square.EXAMPLES:
A singular matrix over the field
QQ
.sage: A = matrix(QQ, 4, [-1,2,-3,6, 0,-1,-1,0, -1,1,-5,7, -1,6,5,2]) sage: A.is_singular() True sage: A.right_kernel().dimension() 1
>>> from sage.all import * >>> A = matrix(QQ, Integer(4), [-Integer(1),Integer(2),-Integer(3),Integer(6), Integer(0),-Integer(1),-Integer(1),Integer(0), -Integer(1),Integer(1),-Integer(5),Integer(7), -Integer(1),Integer(6),Integer(5),Integer(2)]) >>> A.is_singular() True >>> A.right_kernel().dimension() 1
A matrix that is not singular, i.e. nonsingular, over a field.
sage: B = matrix(QQ, 4, [1,-3,-1,-5, 2,-5,-2,-7, -2,5,3,4, -1,4,2,6]) sage: B.is_singular() False sage: B.left_kernel().dimension() 0
>>> from sage.all import * >>> B = matrix(QQ, Integer(4), [Integer(1),-Integer(3),-Integer(1),-Integer(5), Integer(2),-Integer(5),-Integer(2),-Integer(7), -Integer(2),Integer(5),Integer(3),Integer(4), -Integer(1),Integer(4),Integer(2),Integer(6)]) >>> B.is_singular() False >>> B.left_kernel().dimension() 0
For rectangular matrices, invertibility is always
False
, but asking about singularity will give an error.sage: C = matrix(QQ, 5, range(30)) sage: C.is_invertible() False sage: C.is_singular() Traceback (most recent call last): ... ValueError: self must be a square matrix
>>> from sage.all import * >>> C = matrix(QQ, Integer(5), range(Integer(30))) >>> C.is_invertible() False >>> C.is_singular() Traceback (most recent call last): ... ValueError: self must be a square matrix
When the base ring is not a field, then a matrix may be both not invertible and not singular.
sage: D = matrix(ZZ, 4, [2,0,-4,8, 2,1,-2,7, 2,5,7,0, 0,1,4,-6]) sage: D.is_invertible() False sage: D.is_singular() False sage: d = D.determinant(); d 2 sage: d.is_unit() False
>>> from sage.all import * >>> D = matrix(ZZ, Integer(4), [Integer(2),Integer(0),-Integer(4),Integer(8), Integer(2),Integer(1),-Integer(2),Integer(7), Integer(2),Integer(5),Integer(7),Integer(0), Integer(0),Integer(1),Integer(4),-Integer(6)]) >>> D.is_invertible() False >>> D.is_singular() False >>> d = D.determinant(); d 2 >>> d.is_unit() False
- is_skew_hermitian()[source]¶
Return
True
if the matrix is equal to the negative of its conjugate transpose.OUTPUT:
True
if the matrix is square and equal to the negative of its conjugate transpose, andFalse
otherwise.Note that if conjugation has no effect on elements of the base ring (such as for integers), then the
is_skew_symmetric()
method is equivalent and faster.This routine is for matrices over exact rings and so may not work properly for matrices over
RR
orCC
. For matrices with approximate entries, the rings of double-precision floating-point numbers,RDF
andCDF
, are a better choice since thesage.matrix.matrix_double_dense.Matrix_double_dense.is_skew_hermitian()
method has a tolerance parameter. This provides control over allowing for minor discrepancies between entries when checking equality.The result is cached.
EXAMPLES:
sage: A = matrix(QQbar, [[0, -1], # needs sage.rings.number_field ....: [1, 0]]) sage: A.is_skew_hermitian() # needs sage.rings.number_field True
>>> from sage.all import * >>> A = matrix(QQbar, [[Integer(0), -Integer(1)], # needs sage.rings.number_field ... [Integer(1), Integer(0)]]) >>> A.is_skew_hermitian() # needs sage.rings.number_field True
A matrix that is nearly skew-Hermitian, but for a non-real diagonal entry.
sage: # needs sage.rings.number_field sage: A = matrix(QQbar, [[ -I, -1, 1-I], ....: [ 1, 1, -1], ....: [-1-I, 1, -I]]) sage: A.is_skew_hermitian() False sage: A[1, 1] = -I sage: A.is_skew_hermitian() True
>>> from sage.all import * >>> # needs sage.rings.number_field >>> A = matrix(QQbar, [[ -I, -Integer(1), Integer(1)-I], ... [ Integer(1), Integer(1), -Integer(1)], ... [-Integer(1)-I, Integer(1), -I]]) >>> A.is_skew_hermitian() False >>> A[Integer(1), Integer(1)] = -I >>> A.is_skew_hermitian() True
Rectangular matrices are never skew-Hermitian.
sage: A = matrix(QQbar, 3, 4) # needs sage.rings.number_field sage: A.is_skew_hermitian() # needs sage.rings.number_field False
>>> from sage.all import * >>> A = matrix(QQbar, Integer(3), Integer(4)) # needs sage.rings.number_field >>> A.is_skew_hermitian() # needs sage.rings.number_field False
A square, empty matrix is trivially Hermitian.
sage: A = matrix(QQ, 0, 0) sage: A.is_skew_hermitian() True
>>> from sage.all import * >>> A = matrix(QQ, Integer(0), Integer(0)) >>> A.is_skew_hermitian() True
- is_skew_symmetric()[source]¶
Return
True
ifself
is a skew-symmetric matrix.Here, “skew-symmetric matrix” means a square matrix \(A\) satisfying \(A^T = -A\). It does not require that the diagonal entries of \(A\) are \(0\) (although this automatically follows from \(A^T = -A\) when \(2\) is invertible in the ground ring over which the matrix is considered). Skew-symmetric matrices \(A\) whose diagonal entries are \(0\) are said to be “alternating”, and this property is checked by the
is_alternating()
method.EXAMPLES:
sage: m = matrix(QQ, [[0,2], [-2,0]]) sage: m.is_skew_symmetric() True sage: m = matrix(QQ, [[1,2], [2,1]]) sage: m.is_skew_symmetric() False
>>> from sage.all import * >>> m = matrix(QQ, [[Integer(0),Integer(2)], [-Integer(2),Integer(0)]]) >>> m.is_skew_symmetric() True >>> m = matrix(QQ, [[Integer(1),Integer(2)], [Integer(2),Integer(1)]]) >>> m.is_skew_symmetric() False
Skew-symmetric is not the same as alternating when \(2\) is a zero-divisor in the ground ring:
sage: n = matrix(Zmod(4), [[0, 1], [-1, 2]]) sage: n.is_skew_symmetric() True
>>> from sage.all import * >>> n = matrix(Zmod(Integer(4)), [[Integer(0), Integer(1)], [-Integer(1), Integer(2)]]) >>> n.is_skew_symmetric() True
but yet the diagonal cannot be completely arbitrary in this case:
sage: n = matrix(Zmod(4), [[0, 1], [-1, 3]]) sage: n.is_skew_symmetric() False
>>> from sage.all import * >>> n = matrix(Zmod(Integer(4)), [[Integer(0), Integer(1)], [-Integer(1), Integer(3)]]) >>> n.is_skew_symmetric() False
- is_skew_symmetrizable(return_diag=False, positive=True)[source]¶
This function takes a square matrix over an ordered integral domain and checks if it is skew-symmetrizable. A matrix \(B\) is skew-symmetrizable iff there exists an invertible diagonal matrix \(D\) such that \(DB\) is skew-symmetric.
Warning
Expects
self
to be a matrix over an ordered integral domain.INPUT:
return_diag
– boolean (default:False
); ifTrue
andself
is skew-symmetrizable the diagonal entries of the matrix \(D\) are returnedpositive
– boolean (default:True
); ifTrue
, the condition that \(D\) has positive entries is added
OUTPUT:
True
– ifself
is skew-symmetrizable andreturn_diag
isFalse
the diagonal entries of a matrix \(D\) such that \(DB\) is skew-symmetric – iff
self
is skew-symmetrizable andreturn_diag
isTrue
False
– iffself
is not skew-symmetrizable
EXAMPLES:
sage: matrix([[0,6],[3,0]]).is_skew_symmetrizable(positive=False) True sage: matrix([[0,6],[3,0]]).is_skew_symmetrizable(positive=True) False sage: M = matrix(4, [0,1,0,0, -1,0,-1,0, 0,2,0,1, 0,0,-1,0]); M [ 0 1 0 0] [-1 0 -1 0] [ 0 2 0 1] [ 0 0 -1 0] sage: M.is_skew_symmetrizable(return_diag=True) [1, 1, 1/2, 1/2] sage: M2 = diagonal_matrix([1,1,1/2,1/2]) * M; M2 [ 0 1 0 0] [ -1 0 -1 0] [ 0 1 0 1/2] [ 0 0 -1/2 0] sage: M2.is_skew_symmetric() True
>>> from sage.all import * >>> matrix([[Integer(0),Integer(6)],[Integer(3),Integer(0)]]).is_skew_symmetrizable(positive=False) True >>> matrix([[Integer(0),Integer(6)],[Integer(3),Integer(0)]]).is_skew_symmetrizable(positive=True) False >>> M = matrix(Integer(4), [Integer(0),Integer(1),Integer(0),Integer(0), -Integer(1),Integer(0),-Integer(1),Integer(0), Integer(0),Integer(2),Integer(0),Integer(1), Integer(0),Integer(0),-Integer(1),Integer(0)]); M [ 0 1 0 0] [-1 0 -1 0] [ 0 2 0 1] [ 0 0 -1 0] >>> M.is_skew_symmetrizable(return_diag=True) [1, 1, 1/2, 1/2] >>> M2 = diagonal_matrix([Integer(1),Integer(1),Integer(1)/Integer(2),Integer(1)/Integer(2)]) * M; M2 [ 0 1 0 0] [ -1 0 -1 0] [ 0 1 0 1/2] [ 0 0 -1/2 0] >>> M2.is_skew_symmetric() True
REFERENCES:
- is_sparse()[source]¶
Return
True
if this is a sparse matrix.In Sage, being sparse is a property of the underlying representation, not the number of nonzero entries.
EXAMPLES:
sage: matrix(QQ, 2, 2, range(4)).is_sparse() False sage: matrix(QQ, 2, 2, range(4), sparse=True).is_sparse() True
>>> from sage.all import * >>> matrix(QQ, Integer(2), Integer(2), range(Integer(4))).is_sparse() False >>> matrix(QQ, Integer(2), Integer(2), range(Integer(4)), sparse=True).is_sparse() True
- is_square()[source]¶
Return
True
precisely if this matrix is square, i.e., has the same number of rows and columns.EXAMPLES:
sage: matrix(QQ, 2, 2, range(4)).is_square() True sage: matrix(QQ, 2, 3, range(6)).is_square() False
>>> from sage.all import * >>> matrix(QQ, Integer(2), Integer(2), range(Integer(4))).is_square() True >>> matrix(QQ, Integer(2), Integer(3), range(Integer(6))).is_square() False
- is_symmetric()[source]¶
Return
True
if this is a symmetric matrix.A symmetric matrix is necessarily square.
EXAMPLES:
sage: m = Matrix(QQ, 2, range(0,4)) sage: m.is_symmetric() False sage: m = Matrix(QQ, 2, (1,1,1,1,1,1)) sage: m.is_symmetric() False sage: m = Matrix(QQ, 1, (2,)) sage: m.is_symmetric() True
>>> from sage.all import * >>> m = Matrix(QQ, Integer(2), range(Integer(0),Integer(4))) >>> m.is_symmetric() False >>> m = Matrix(QQ, Integer(2), (Integer(1),Integer(1),Integer(1),Integer(1),Integer(1),Integer(1))) >>> m.is_symmetric() False >>> m = Matrix(QQ, Integer(1), (Integer(2),)) >>> m.is_symmetric() True
- is_symmetrizable(return_diag=False, positive=True)[source]¶
This function takes a square matrix over an ordered integral domain and checks if it is symmetrizable.
A matrix \(B\) is symmetrizable iff there exists an invertible diagonal matrix \(D\) such that \(DB\) is symmetric.
Warning
Expects
self
to be a matrix over an ordered integral domain.INPUT:
return_diag
– boolean (default:False
); ifTrue
andself
is symmetrizable the diagonal entries of the matrix \(D\) are returnedpositive
– boolean (default:True
); ifTrue
, the condition that \(D\) has positive entries is added
OUTPUT:
True
– ifself
is symmetrizable andreturn_diag
isFalse
the diagonal entries of a matrix \(D\) such that \(DB\) is symmetric – iff
self
is symmetrizable andreturn_diag
isTrue
False
– iffself
is not symmetrizable
EXAMPLES:
sage: matrix([[0,6],[3,0]]).is_symmetrizable(positive=False) True sage: matrix([[0,6],[3,0]]).is_symmetrizable(positive=True) True sage: matrix([[0,6],[0,0]]).is_symmetrizable(return_diag=True) False sage: matrix([2]).is_symmetrizable(positive=True) True sage: matrix([[1,2],[3,4]]).is_symmetrizable(return_diag=true) [1, 2/3]
>>> from sage.all import * >>> matrix([[Integer(0),Integer(6)],[Integer(3),Integer(0)]]).is_symmetrizable(positive=False) True >>> matrix([[Integer(0),Integer(6)],[Integer(3),Integer(0)]]).is_symmetrizable(positive=True) True >>> matrix([[Integer(0),Integer(6)],[Integer(0),Integer(0)]]).is_symmetrizable(return_diag=True) False >>> matrix([Integer(2)]).is_symmetrizable(positive=True) True >>> matrix([[Integer(1),Integer(2)],[Integer(3),Integer(4)]]).is_symmetrizable(return_diag=true) [1, 2/3]
REFERENCES:
- is_unit()[source]¶
Return
True
if this matrix is invertible.EXAMPLES: The following matrix is invertible over \(\QQ\) but not over \(\ZZ\).
sage: A = MatrixSpace(ZZ, 2)(range(4)) sage: A.is_invertible() False sage: A.matrix_over_field().is_invertible() True
>>> from sage.all import * >>> A = MatrixSpace(ZZ, Integer(2))(range(Integer(4))) >>> A.is_invertible() False >>> A.matrix_over_field().is_invertible() True
The inverse function is a constructor for matrices over the fraction field, so it can work even if A is not invertible.
sage: ~A # inverse of A [-3/2 1/2] [ 1 0]
>>> from sage.all import * >>> ~A # inverse of A [-3/2 1/2] [ 1 0]
The next matrix is invertible over \(\ZZ\).
sage: A = MatrixSpace(IntegerRing(), 2)([1,10,0,-1]) sage: A.is_invertible() True sage: ~A # compute the inverse [ 1 10] [ 0 -1]
>>> from sage.all import * >>> A = MatrixSpace(IntegerRing(), Integer(2))([Integer(1),Integer(10),Integer(0),-Integer(1)]) >>> A.is_invertible() True >>> ~A # compute the inverse [ 1 10] [ 0 -1]
The following nontrivial matrix is invertible over \(\ZZ[x]\).
sage: R.<x> = PolynomialRing(IntegerRing()) sage: A = MatrixSpace(R, 2)([1,x,0,-1]) sage: A.is_invertible() True sage: ~A [ 1 x] [ 0 -1]
>>> from sage.all import * >>> R = PolynomialRing(IntegerRing(), names=('x',)); (x,) = R._first_ngens(1) >>> A = MatrixSpace(R, Integer(2))([Integer(1),x,Integer(0),-Integer(1)]) >>> A.is_invertible() True >>> ~A [ 1 x] [ 0 -1]
- items()[source]¶
Return an iterable of
((i,j), value)
elements.This may (but is not guaranteed to) suppress zero values.
EXAMPLES:
sage: a = matrix(QQ['x,y'], 2, range(6), sparse=True); a [0 1 2] [3 4 5] sage: list(a.items()) [((0, 1), 1), ((0, 2), 2), ((1, 0), 3), ((1, 1), 4), ((1, 2), 5)]
>>> from sage.all import * >>> a = matrix(QQ['x,y'], Integer(2), range(Integer(6)), sparse=True); a [0 1 2] [3 4 5] >>> list(a.items()) [((0, 1), 1), ((0, 2), 2), ((1, 0), 3), ((1, 1), 4), ((1, 2), 5)]
- iterates(v, n, rows=True)[source]¶
Let \(A\) be this matrix and \(v\) be a free module element. If rows is True, return a matrix whose rows are the entries of the following vectors:
\[v, v A, v A^2, \dots, v A^{n-1}.\]If rows is False, return a matrix whose columns are the entries of the following vectors:
\[v, Av, A^2 v, \dots, A^{n-1} v.\]INPUT:
v
– free module elementn
– nonnegative integer
EXAMPLES:
sage: A = matrix(ZZ, 2, [1,1,3,5]); A [1 1] [3 5] sage: v = vector([1,0]) sage: A.iterates(v, 0) [] sage: A.iterates(v, 5) [ 1 0] [ 1 1] [ 4 6] [ 22 34] [124 192]
>>> from sage.all import * >>> A = matrix(ZZ, Integer(2), [Integer(1),Integer(1),Integer(3),Integer(5)]); A [1 1] [3 5] >>> v = vector([Integer(1),Integer(0)]) >>> A.iterates(v, Integer(0)) [] >>> A.iterates(v, Integer(5)) [ 1 0] [ 1 1] [ 4 6] [ 22 34] [124 192]
Another example:
sage: a = matrix(ZZ, 3, range(9)); a [0 1 2] [3 4 5] [6 7 8] sage: v = vector([1,0,0]) sage: a.iterates(v, 4) [ 1 0 0] [ 0 1 2] [ 15 18 21] [180 234 288] sage: a.iterates(v, 4, rows=False) [ 1 0 15 180] [ 0 3 42 558] [ 0 6 69 936]
>>> from sage.all import * >>> a = matrix(ZZ, Integer(3), range(Integer(9))); a [0 1 2] [3 4 5] [6 7 8] >>> v = vector([Integer(1),Integer(0),Integer(0)]) >>> a.iterates(v, Integer(4)) [ 1 0 0] [ 0 1 2] [ 15 18 21] [180 234 288] >>> a.iterates(v, Integer(4), rows=False) [ 1 0 15 180] [ 0 3 42 558] [ 0 6 69 936]
- linear_combination_of_columns(v)[source]¶
Return the linear combination of the columns of
self
given by the coefficients in the listv
.INPUT:
v
– a list of scalars. The length can be less than the number of columns ofself
but not greater.
OUTPUT:
The vector (or free module element) that is a linear combination of the columns of
self
. If the list of scalars has fewer entries than the number of columns, additional zeros are appended to the list until it has as many entries as the number of columns.EXAMPLES:
sage: a = matrix(ZZ, 2, 3, range(6)); a [0 1 2] [3 4 5] sage: a.linear_combination_of_columns([1,1,1]) (3, 12) sage: a.linear_combination_of_columns([0,0,0]) (0, 0) sage: a.linear_combination_of_columns([1/2,2/3,3/4]) (13/6, 95/12)
>>> from sage.all import * >>> a = matrix(ZZ, Integer(2), Integer(3), range(Integer(6))); a [0 1 2] [3 4 5] >>> a.linear_combination_of_columns([Integer(1),Integer(1),Integer(1)]) (3, 12) >>> a.linear_combination_of_columns([Integer(0),Integer(0),Integer(0)]) (0, 0) >>> a.linear_combination_of_columns([Integer(1)/Integer(2),Integer(2)/Integer(3),Integer(3)/Integer(4)]) (13/6, 95/12)
The list
v
can be anything that is iterable. Perhaps most naturally, a vector may be used.sage: v = vector(ZZ, [1,2,3]) sage: a.linear_combination_of_columns(v) (8, 26)
>>> from sage.all import * >>> v = vector(ZZ, [Integer(1),Integer(2),Integer(3)]) >>> a.linear_combination_of_columns(v) (8, 26)
We check that a matrix with no columns behaves properly.
sage: matrix(QQ, 2, 0).linear_combination_of_columns([]) (0, 0)
>>> from sage.all import * >>> matrix(QQ, Integer(2), Integer(0)).linear_combination_of_columns([]) (0, 0)
The object returned is a vector, or a free module element.
sage: B = matrix(ZZ, 4, 3, range(12)) sage: w = B.linear_combination_of_columns([-1,2,-3]) sage: w (-4, -10, -16, -22) sage: w.parent() Ambient free module of rank 4 over the principal ideal domain Integer Ring sage: x = B.linear_combination_of_columns([1/2,1/3,1/4]) sage: x (5/6, 49/12, 22/3, 127/12) sage: x.parent() Vector space of dimension 4 over Rational Field
>>> from sage.all import * >>> B = matrix(ZZ, Integer(4), Integer(3), range(Integer(12))) >>> w = B.linear_combination_of_columns([-Integer(1),Integer(2),-Integer(3)]) >>> w (-4, -10, -16, -22) >>> w.parent() Ambient free module of rank 4 over the principal ideal domain Integer Ring >>> x = B.linear_combination_of_columns([Integer(1)/Integer(2),Integer(1)/Integer(3),Integer(1)/Integer(4)]) >>> x (5/6, 49/12, 22/3, 127/12) >>> x.parent() Vector space of dimension 4 over Rational Field
The length of v can be less than the number of columns, but not greater.
sage: A = matrix(QQ, 3, 5, range(15)) sage: A.linear_combination_of_columns([1,-2,3,-4]) (-8, -18, -28) sage: A.linear_combination_of_columns([1,2,3,4,5,6]) Traceback (most recent call last): ... ValueError: length of v must be at most the number of columns of self
>>> from sage.all import * >>> A = matrix(QQ, Integer(3), Integer(5), range(Integer(15))) >>> A.linear_combination_of_columns([Integer(1),-Integer(2),Integer(3),-Integer(4)]) (-8, -18, -28) >>> A.linear_combination_of_columns([Integer(1),Integer(2),Integer(3),Integer(4),Integer(5),Integer(6)]) Traceback (most recent call last): ... ValueError: length of v must be at most the number of columns of self
- linear_combination_of_rows(v)[source]¶
Return the linear combination of the rows of
self
given by the coefficients in the listv
.INPUT:
v
– a list of scalars. The length can be less than the number of rows ofself
but not greater.
OUTPUT:
The vector (or free module element) that is a linear combination of the rows of
self
. If the list of scalars has fewer entries than the number of rows, additional zeros are appended to the list until it has as many entries as the number of rows.EXAMPLES:
sage: a = matrix(ZZ, 2, 3, range(6)); a [0 1 2] [3 4 5] sage: a.linear_combination_of_rows([1,2]) (6, 9, 12) sage: a.linear_combination_of_rows([0,0]) (0, 0, 0) sage: a.linear_combination_of_rows([1/2,2/3]) (2, 19/6, 13/3)
>>> from sage.all import * >>> a = matrix(ZZ, Integer(2), Integer(3), range(Integer(6))); a [0 1 2] [3 4 5] >>> a.linear_combination_of_rows([Integer(1),Integer(2)]) (6, 9, 12) >>> a.linear_combination_of_rows([Integer(0),Integer(0)]) (0, 0, 0) >>> a.linear_combination_of_rows([Integer(1)/Integer(2),Integer(2)/Integer(3)]) (2, 19/6, 13/3)
The list
v
can be anything that is iterable. Perhaps most naturally, a vector may be used.sage: v = vector(ZZ, [1,2]) sage: a.linear_combination_of_rows(v) (6, 9, 12)
>>> from sage.all import * >>> v = vector(ZZ, [Integer(1),Integer(2)]) >>> a.linear_combination_of_rows(v) (6, 9, 12)
We check that a matrix with no rows behaves properly.
sage: matrix(QQ, 0, 2).linear_combination_of_rows([]) (0, 0)
>>> from sage.all import * >>> matrix(QQ, Integer(0), Integer(2)).linear_combination_of_rows([]) (0, 0)
The object returned is a vector, or a free module element.
sage: B = matrix(ZZ, 4, 3, range(12)) sage: w = B.linear_combination_of_rows([-1,2,-3,4]) sage: w (24, 26, 28) sage: w.parent() Ambient free module of rank 3 over the principal ideal domain Integer Ring sage: x = B.linear_combination_of_rows([1/2,1/3,1/4,1/5]) sage: x (43/10, 67/12, 103/15) sage: x.parent() Vector space of dimension 3 over Rational Field
>>> from sage.all import * >>> B = matrix(ZZ, Integer(4), Integer(3), range(Integer(12))) >>> w = B.linear_combination_of_rows([-Integer(1),Integer(2),-Integer(3),Integer(4)]) >>> w (24, 26, 28) >>> w.parent() Ambient free module of rank 3 over the principal ideal domain Integer Ring >>> x = B.linear_combination_of_rows([Integer(1)/Integer(2),Integer(1)/Integer(3),Integer(1)/Integer(4),Integer(1)/Integer(5)]) >>> x (43/10, 67/12, 103/15) >>> x.parent() Vector space of dimension 3 over Rational Field
The length of v can be less than the number of rows, but not greater.
sage: A = matrix(QQ, 3, 4, range(12)) sage: A.linear_combination_of_rows([2,3]) (12, 17, 22, 27) sage: A.linear_combination_of_rows([1,2,3,4]) Traceback (most recent call last): ... ValueError: length of v must be at most the number of rows of self
>>> from sage.all import * >>> A = matrix(QQ, Integer(3), Integer(4), range(Integer(12))) >>> A.linear_combination_of_rows([Integer(2),Integer(3)]) (12, 17, 22, 27) >>> A.linear_combination_of_rows([Integer(1),Integer(2),Integer(3),Integer(4)]) Traceback (most recent call last): ... ValueError: length of v must be at most the number of rows of self
- list()[source]¶
List of the elements of
self
ordered by elements in each row. It is safe to change the returned list.Warning
This function returns a list of the entries in the matrix
self
. It does not return a list of the rows ofself
, so it is different than the output oflist(self)
, which returns[self[0],self[1],...]
.EXAMPLES:
sage: R.<x,y> = QQ[] sage: a = matrix(R,2,[x,y,x*y, y,x,2*x+y]); a [ x y x*y] [ y x 2*x + y] sage: v = a.list(); v [x, y, x*y, y, x, 2*x + y]
>>> from sage.all import * >>> R = QQ['x, y']; (x, y,) = R._first_ngens(2) >>> a = matrix(R,Integer(2),[x,y,x*y, y,x,Integer(2)*x+y]); a [ x y x*y] [ y x 2*x + y] >>> v = a.list(); v [x, y, x*y, y, x, 2*x + y]
Note that list(a) is different than a.list():
sage: a.list() [x, y, x*y, y, x, 2*x + y] sage: list(a) [(x, y, x*y), (y, x, 2*x + y)]
>>> from sage.all import * >>> a.list() [x, y, x*y, y, x, 2*x + y] >>> list(a) [(x, y, x*y), (y, x, 2*x + y)]
Notice that changing the returned list does not change a (the list is a copy):
sage: v[0] = 25 sage: a [ x y x*y] [ y x 2*x + y]
>>> from sage.all import * >>> v[Integer(0)] = Integer(25) >>> a [ x y x*y] [ y x 2*x + y]
- mod(p)[source]¶
Return matrix mod \(p\), over the reduced ring.
EXAMPLES:
sage: M = matrix(ZZ, 2, 2, [5, 9, 13, 15]) sage: M.mod(7) [5 2] [6 1] sage: parent(M.mod(7)) Full MatrixSpace of 2 by 2 dense matrices over Ring of integers modulo 7
>>> from sage.all import * >>> M = matrix(ZZ, Integer(2), Integer(2), [Integer(5), Integer(9), Integer(13), Integer(15)]) >>> M.mod(Integer(7)) [5 2] [6 1] >>> parent(M.mod(Integer(7))) Full MatrixSpace of 2 by 2 dense matrices over Ring of integers modulo 7
- monomial_coefficients(copy=True)[source]¶
Dictionary of the elements of
self
with keys pairs(i,j)
and values the nonzero entries ofself
.INPUT:
copy
– boolean (default:True
); make a copy of thedict
corresponding toself
If
copy=True
, then is safe to change the returned dictionary. Otherwise, this can cause undesired behavior by mutating thedict
.EXAMPLES:
sage: R.<x,y> = QQ[] sage: a = matrix(R,2,[x,y,0, 0,0,2*x+y]); a [ x y 0] [ 0 0 2*x + y] sage: d = a.dict(); d {(0, 0): x, (0, 1): y, (1, 2): 2*x + y}
>>> from sage.all import * >>> R = QQ['x, y']; (x, y,) = R._first_ngens(2) >>> a = matrix(R,Integer(2),[x,y,Integer(0), Integer(0),Integer(0),Integer(2)*x+y]); a [ x y 0] [ 0 0 2*x + y] >>> d = a.dict(); d {(0, 0): x, (0, 1): y, (1, 2): 2*x + y}
Notice that changing the returned list does not change a (the list is a copy):
sage: d[0,0] = 25 sage: a [ x y 0] [ 0 0 2*x + y]
>>> from sage.all import * >>> d[Integer(0),Integer(0)] = Integer(25) >>> a [ x y 0] [ 0 0 2*x + y]
- multiplicative_order()[source]¶
Return the multiplicative order of this matrix, which must therefore be invertible.
Only implemented over finite fields and over \(\ZZ\).
EXAMPLES:
Over finite fields:
sage: A = matrix(GF(59), 3, [10,56,39,53,56,33,58,24,55]) sage: A.multiplicative_order() # needs sage.libs.pari 580 sage: (A^580).is_one() True sage: B = matrix(GF(10007^3, 'b'), 0) # needs sage.rings.finite_rings sage: B.multiplicative_order() # needs sage.rings.finite_rings 1 sage: # needs sage.rings.finite_rings sage: M = MatrixSpace(GF(11^2, 'e'), 5) sage: E = M.random_element() sage: while E.det() == 0: ....: E = M.random_element() sage: (E^E.multiplicative_order()).is_one() True
>>> from sage.all import * >>> A = matrix(GF(Integer(59)), Integer(3), [Integer(10),Integer(56),Integer(39),Integer(53),Integer(56),Integer(33),Integer(58),Integer(24),Integer(55)]) >>> A.multiplicative_order() # needs sage.libs.pari 580 >>> (A**Integer(580)).is_one() True >>> B = matrix(GF(Integer(10007)**Integer(3), 'b'), Integer(0)) # needs sage.rings.finite_rings >>> B.multiplicative_order() # needs sage.rings.finite_rings 1 >>> # needs sage.rings.finite_rings >>> M = MatrixSpace(GF(Integer(11)**Integer(2), 'e'), Integer(5)) >>> E = M.random_element() >>> while E.det() == Integer(0): ... E = M.random_element() >>> (E**E.multiplicative_order()).is_one() True
Over \(\ZZ\):
sage: m = matrix(ZZ, 2, 2, [-1,1,-1,0]) sage: m.multiplicative_order() # needs sage.libs.pari 3 sage: m = posets.ChainPoset(6).coxeter_transformation() # needs sage.combinat sage.graphs sage: m.multiplicative_order() # needs sage.combinat sage.graphs sage.groups 7 sage: P = posets.TamariLattice(4).coxeter_transformation() # needs sage.combinat sage.graphs sage: P.multiplicative_order() # needs sage.combinat sage.graphs sage.groups 10 sage: M = matrix(ZZ, 2, 2, [1, 1, 0, 1]) sage: M.multiplicative_order() # needs sage.libs.pari +Infinity sage: for k in range(600): # needs sage.groups sage.modular ....: m = SL2Z.random_element() ....: o = m.multiplicative_order() ....: if o != Infinity and m**o != SL2Z.one(): ....: raise RuntimeError sage: m24 = matrix.companion(cyclotomic_polynomial(24)) sage: def val(i, j): ....: if i < j: ....: return 0 ....: elif i == j: ....: return 1 ....: else: ....: return ZZ.random_element(-100,100) sage: rnd = matrix(ZZ, 8, 8, val) sage: (rnd * m24 * rnd.inverse_of_unit()).multiplicative_order() # needs sage.libs.pari 24
>>> from sage.all import * >>> m = matrix(ZZ, Integer(2), Integer(2), [-Integer(1),Integer(1),-Integer(1),Integer(0)]) >>> m.multiplicative_order() # needs sage.libs.pari 3 >>> m = posets.ChainPoset(Integer(6)).coxeter_transformation() # needs sage.combinat sage.graphs >>> m.multiplicative_order() # needs sage.combinat sage.graphs sage.groups 7 >>> P = posets.TamariLattice(Integer(4)).coxeter_transformation() # needs sage.combinat sage.graphs >>> P.multiplicative_order() # needs sage.combinat sage.graphs sage.groups 10 >>> M = matrix(ZZ, Integer(2), Integer(2), [Integer(1), Integer(1), Integer(0), Integer(1)]) >>> M.multiplicative_order() # needs sage.libs.pari +Infinity >>> for k in range(Integer(600)): # needs sage.groups sage.modular ... m = SL2Z.random_element() ... o = m.multiplicative_order() ... if o != Infinity and m**o != SL2Z.one(): ... raise RuntimeError >>> m24 = matrix.companion(cyclotomic_polynomial(Integer(24))) >>> def val(i, j): ... if i < j: ... return Integer(0) ... elif i == j: ... return Integer(1) ... else: ... return ZZ.random_element(-Integer(100),Integer(100)) >>> rnd = matrix(ZZ, Integer(8), Integer(8), val) >>> (rnd * m24 * rnd.inverse_of_unit()).multiplicative_order() # needs sage.libs.pari 24
REFERENCES:
- mutate(k)[source]¶
Mutates
self
at row and column indexk
.Warning
Only makes sense if
self
is skew-symmetrizable.INPUT:
k
– integer at which row/columnself
is mutated
EXAMPLES:
Mutation of the B-matrix of the quiver of type \(A_3\):
sage: M = matrix(ZZ, 3, [0,1,0,-1,0,-1,0,1,0]); M [ 0 1 0] [-1 0 -1] [ 0 1 0] sage: M.mutate(0); M [ 0 -1 0] [ 1 0 -1] [ 0 1 0] sage: M.mutate(1); M [ 0 1 -1] [-1 0 1] [ 1 -1 0] sage: M = matrix(ZZ, 6, [0,1,0,-1,0,-1,0,1,0,1,0,0,0,1,0,0,0,1]); M [ 0 1 0] [-1 0 -1] [ 0 1 0] [ 1 0 0] [ 0 1 0] [ 0 0 1] sage: M.mutate(0); M [ 0 -1 0] [ 1 0 -1] [ 0 1 0] [-1 1 0] [ 0 1 0] [ 0 0 1]
>>> from sage.all import * >>> M = matrix(ZZ, Integer(3), [Integer(0),Integer(1),Integer(0),-Integer(1),Integer(0),-Integer(1),Integer(0),Integer(1),Integer(0)]); M [ 0 1 0] [-1 0 -1] [ 0 1 0] >>> M.mutate(Integer(0)); M [ 0 -1 0] [ 1 0 -1] [ 0 1 0] >>> M.mutate(Integer(1)); M [ 0 1 -1] [-1 0 1] [ 1 -1 0] >>> M = matrix(ZZ, Integer(6), [Integer(0),Integer(1),Integer(0),-Integer(1),Integer(0),-Integer(1),Integer(0),Integer(1),Integer(0),Integer(1),Integer(0),Integer(0),Integer(0),Integer(1),Integer(0),Integer(0),Integer(0),Integer(1)]); M [ 0 1 0] [-1 0 -1] [ 0 1 0] [ 1 0 0] [ 0 1 0] [ 0 0 1] >>> M.mutate(Integer(0)); M [ 0 -1 0] [ 1 0 -1] [ 0 1 0] [-1 1 0] [ 0 1 0] [ 0 0 1]
REFERENCES:
- ncols()[source]¶
Return the number of columns of this matrix.
EXAMPLES:
sage: M = MatrixSpace(QQ, 2, 3) sage: A = M([1,2,3, 4,5,6]) sage: A [1 2 3] [4 5 6] sage: A.ncols() 3 sage: A.nrows() 2
>>> from sage.all import * >>> M = MatrixSpace(QQ, Integer(2), Integer(3)) >>> A = M([Integer(1),Integer(2),Integer(3), Integer(4),Integer(5),Integer(6)]) >>> A [1 2 3] [4 5 6] >>> A.ncols() 3 >>> A.nrows() 2
AUTHORS:
Naqi Jaffery (2006-01-24): examples
- nonpivots()[source]¶
Return the list of \(i\) such that the \(i\)-th column of
self
is NOT a pivot column of the reduced row echelon form ofself
.OUTPUT: sorted tuple of (Python) integers
EXAMPLES:
sage: a = matrix(QQ, 3, 3, range(9)); a [0 1 2] [3 4 5] [6 7 8] sage: a.echelon_form() [ 1 0 -1] [ 0 1 2] [ 0 0 0] sage: a.nonpivots() (2,)
>>> from sage.all import * >>> a = matrix(QQ, Integer(3), Integer(3), range(Integer(9))); a [0 1 2] [3 4 5] [6 7 8] >>> a.echelon_form() [ 1 0 -1] [ 0 1 2] [ 0 0 0] >>> a.nonpivots() (2,)
- nonzero_positions(copy=True, column_order=False)[source]¶
Return the sorted list of pairs
(i,j)
such thatself[i,j] != 0
.INPUT:
copy
– boolean (default:True
); it is safe to change the resulting list (unless you give the optioncopy=False
)column_order
– boolean (default:False
); ifTrue
, returns the list of pairs(i,j)
such thatself[i,j] != 0
, but sorted by columns, i.e., columnj=0
entries occur first, then columnj=1
entries, etc.
EXAMPLES:
sage: a = matrix(QQ, 2,3, [1,2,0,2,0,0]); a [1 2 0] [2 0 0] sage: a.nonzero_positions() [(0, 0), (0, 1), (1, 0)] sage: a.nonzero_positions(copy=False) [(0, 0), (0, 1), (1, 0)] sage: a.nonzero_positions(column_order=True) [(0, 0), (1, 0), (0, 1)] sage: a = matrix(QQ, 2,3, [1,2,0,2,0,0], sparse=True); a [1 2 0] [2 0 0] sage: a.nonzero_positions() [(0, 0), (0, 1), (1, 0)] sage: a.nonzero_positions(copy=False) [(0, 0), (0, 1), (1, 0)] sage: a.nonzero_positions(column_order=True) [(0, 0), (1, 0), (0, 1)]
>>> from sage.all import * >>> a = matrix(QQ, Integer(2),Integer(3), [Integer(1),Integer(2),Integer(0),Integer(2),Integer(0),Integer(0)]); a [1 2 0] [2 0 0] >>> a.nonzero_positions() [(0, 0), (0, 1), (1, 0)] >>> a.nonzero_positions(copy=False) [(0, 0), (0, 1), (1, 0)] >>> a.nonzero_positions(column_order=True) [(0, 0), (1, 0), (0, 1)] >>> a = matrix(QQ, Integer(2),Integer(3), [Integer(1),Integer(2),Integer(0),Integer(2),Integer(0),Integer(0)], sparse=True); a [1 2 0] [2 0 0] >>> a.nonzero_positions() [(0, 0), (0, 1), (1, 0)] >>> a.nonzero_positions(copy=False) [(0, 0), (0, 1), (1, 0)] >>> a.nonzero_positions(column_order=True) [(0, 0), (1, 0), (0, 1)]
- nonzero_positions_in_column(i)[source]¶
Return a sorted list of the integers
j
such thatself[j,i]
is nonzero, i.e., such that thej
-th position of thei
-th column is nonzero.INPUT:
i
– integer
OUTPUT: list
EXAMPLES:
sage: a = matrix(QQ, 3,2, [1,2,0,2,0,0]); a [1 2] [0 2] [0 0] sage: a.nonzero_positions_in_column(0) [0] sage: a.nonzero_positions_in_column(1) [0, 1]
>>> from sage.all import * >>> a = matrix(QQ, Integer(3),Integer(2), [Integer(1),Integer(2),Integer(0),Integer(2),Integer(0),Integer(0)]); a [1 2] [0 2] [0 0] >>> a.nonzero_positions_in_column(Integer(0)) [0] >>> a.nonzero_positions_in_column(Integer(1)) [0, 1]
You will get an
IndexError
if you select an invalid column:sage: a.nonzero_positions_in_column(2) Traceback (most recent call last): ... IndexError: matrix column index out of range
>>> from sage.all import * >>> a.nonzero_positions_in_column(Integer(2)) Traceback (most recent call last): ... IndexError: matrix column index out of range
- nonzero_positions_in_row(i)[source]¶
Return the integers
j
such thatself[i,j]
is nonzero, i.e., such that thej
-th position of thei
-th row is nonzero.INPUT:
i
– integer
OUTPUT: list
EXAMPLES:
sage: a = matrix(QQ, 3,2, [1,2,0,2,0,0]); a [1 2] [0 2] [0 0] sage: a.nonzero_positions_in_row(0) [0, 1] sage: a.nonzero_positions_in_row(1) [1] sage: a.nonzero_positions_in_row(2) []
>>> from sage.all import * >>> a = matrix(QQ, Integer(3),Integer(2), [Integer(1),Integer(2),Integer(0),Integer(2),Integer(0),Integer(0)]); a [1 2] [0 2] [0 0] >>> a.nonzero_positions_in_row(Integer(0)) [0, 1] >>> a.nonzero_positions_in_row(Integer(1)) [1] >>> a.nonzero_positions_in_row(Integer(2)) []
- nrows()[source]¶
Return the number of rows of this matrix.
EXAMPLES:
sage: M = MatrixSpace(QQ,6,7) sage: A = M([1,2,3,4,5,6,7, 22,3/4,34,11,7,5,3, 99,65,1/2,2/3,3/5,4/5,5/6, 9,8/9, 9/8,7/6,6/7,76,4, 0,9,8,7,6,5,4, 123,99,91,28,6,1024,1]) sage: A [ 1 2 3 4 5 6 7] [ 22 3/4 34 11 7 5 3] [ 99 65 1/2 2/3 3/5 4/5 5/6] [ 9 8/9 9/8 7/6 6/7 76 4] [ 0 9 8 7 6 5 4] [ 123 99 91 28 6 1024 1] sage: A.ncols() 7 sage: A.nrows() 6
>>> from sage.all import * >>> M = MatrixSpace(QQ,Integer(6),Integer(7)) >>> A = M([Integer(1),Integer(2),Integer(3),Integer(4),Integer(5),Integer(6),Integer(7), Integer(22),Integer(3)/Integer(4),Integer(34),Integer(11),Integer(7),Integer(5),Integer(3), Integer(99),Integer(65),Integer(1)/Integer(2),Integer(2)/Integer(3),Integer(3)/Integer(5),Integer(4)/Integer(5),Integer(5)/Integer(6), Integer(9),Integer(8)/Integer(9), Integer(9)/Integer(8),Integer(7)/Integer(6),Integer(6)/Integer(7),Integer(76),Integer(4), Integer(0),Integer(9),Integer(8),Integer(7),Integer(6),Integer(5),Integer(4), Integer(123),Integer(99),Integer(91),Integer(28),Integer(6),Integer(1024),Integer(1)]) >>> A [ 1 2 3 4 5 6 7] [ 22 3/4 34 11 7 5 3] [ 99 65 1/2 2/3 3/5 4/5 5/6] [ 9 8/9 9/8 7/6 6/7 76 4] [ 0 9 8 7 6 5 4] [ 123 99 91 28 6 1024 1] >>> A.ncols() 7 >>> A.nrows() 6
AUTHORS:
Naqi Jaffery (2006-01-24): examples
- permute_columns(permutation)[source]¶
Permute the columns of
self
by applying the permutation group elementpermutation
.As permutation group elements act on integers \(\{1,\dots,n\}\), columns are considered numbered from 1 for this operation.
INPUT:
permutation
– aPermutationGroupElement
EXAMPLES: We create a matrix:
sage: M = matrix(ZZ, [[1,0,0,0,0],[0,2,0,0,0],[0,0,3,0,0],[0,0,0,4,0],[0,0,0,0,5]]) sage: M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
>>> from sage.all import * >>> M = matrix(ZZ, [[Integer(1),Integer(0),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(2),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(3),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(4),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(0),Integer(5)]]) >>> M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
Next of all, create a permutation group element and act on
M
with it:sage: # needs sage.groups sage: G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) sage: sigma, tau = G.gens() sage: sigma (1,2,3)(4,5) sage: M.permute_columns(sigma) sage: M [0 0 1 0 0] [2 0 0 0 0] [0 3 0 0 0] [0 0 0 0 4] [0 0 0 5 0]
>>> from sage.all import * >>> # needs sage.groups >>> G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) >>> sigma, tau = G.gens() >>> sigma (1,2,3)(4,5) >>> M.permute_columns(sigma) >>> M [0 0 1 0 0] [2 0 0 0 0] [0 3 0 0 0] [0 0 0 0 4] [0 0 0 5 0]
- permute_rows(permutation)[source]¶
Permute the rows of
self
by applying the permutation group elementpermutation
.As permutation group elements act on integers \(\{1,\dots,n\}\), rows are considered numbered from 1 for this operation.
INPUT:
permutation
– aPermutationGroupElement
EXAMPLES: We create a matrix:
sage: M = matrix(ZZ, [[1,0,0,0,0],[0,2,0,0,0],[0,0,3,0,0],[0,0,0,4,0],[0,0,0,0,5]]) sage: M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
>>> from sage.all import * >>> M = matrix(ZZ, [[Integer(1),Integer(0),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(2),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(3),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(4),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(0),Integer(5)]]) >>> M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
Next of all, create a permutation group element and act on
M
:sage: # needs sage.groups sage: G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) sage: sigma, tau = G.gens() sage: sigma (1,2,3)(4,5) sage: M.permute_rows(sigma) sage: M [0 2 0 0 0] [0 0 3 0 0] [1 0 0 0 0] [0 0 0 0 5] [0 0 0 4 0]
>>> from sage.all import * >>> # needs sage.groups >>> G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) >>> sigma, tau = G.gens() >>> sigma (1,2,3)(4,5) >>> M.permute_rows(sigma) >>> M [0 2 0 0 0] [0 0 3 0 0] [1 0 0 0 0] [0 0 0 0 5] [0 0 0 4 0]
- permute_rows_and_columns(row_permutation, column_permutation)[source]¶
Permute the rows and columns of
self
by applying the permutation group elementsrow_permutation
andcolumn_permutation
respectively.As permutation group elements act on integers \(\{1,\dots,n\}\), rows and columns are considered numbered from 1 for this operation.
INPUT:
row_permutation
– aPermutationGroupElement
column_permutation
– aPermutationGroupElement
OUTPUT: a matrix
EXAMPLES: We create a matrix:
sage: M = matrix(ZZ, [[1,0,0,0,0],[0,2,0,0,0],[0,0,3,0,0],[0,0,0,4,0],[0,0,0,0,5]]) sage: M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
>>> from sage.all import * >>> M = matrix(ZZ, [[Integer(1),Integer(0),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(2),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(3),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(4),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(0),Integer(5)]]) >>> M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
Next of all, create a permutation group element and act on
M
:sage: # needs sage.groups sage: G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) sage: sigma, tau = G.gens() sage: sigma (1,2,3)(4,5) sage: M.permute_rows_and_columns(sigma,tau) sage: M [2 0 0 0 0] [0 3 0 0 0] [0 0 0 0 1] [0 0 0 5 0] [0 0 4 0 0]
>>> from sage.all import * >>> # needs sage.groups >>> G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) >>> sigma, tau = G.gens() >>> sigma (1,2,3)(4,5) >>> M.permute_rows_and_columns(sigma,tau) >>> M [2 0 0 0 0] [0 3 0 0 0] [0 0 0 0 1] [0 0 0 5 0] [0 0 4 0 0]
- pivots()[source]¶
Return the pivot column positions of this matrix.
OUTPUT: a tuple of Python integers: the position of the first nonzero entry in each row of the echelon form.
This returns a tuple so it is immutable; see Issue #10752.
EXAMPLES:
sage: A = matrix(QQ, 2, 2, range(4)) sage: A.pivots() (0, 1)
>>> from sage.all import * >>> A = matrix(QQ, Integer(2), Integer(2), range(Integer(4))) >>> A.pivots() (0, 1)
- rank()[source]¶
Return the rank of this matrix.
EXAMPLES:
sage: m = matrix(GF(7), 5, range(25)) sage: m.rank() 2
>>> from sage.all import * >>> m = matrix(GF(Integer(7)), Integer(5), range(Integer(25))) >>> m.rank() 2
Rank is not implemented over the integers modulo a composite yet.:
sage: m = matrix(Integers(4), 2, [2,2,2,2]) sage: m.rank() Traceback (most recent call last): ... NotImplementedError: Echelon form not implemented over 'Ring of integers modulo 4'.
>>> from sage.all import * >>> m = matrix(Integers(Integer(4)), Integer(2), [Integer(2),Integer(2),Integer(2),Integer(2)]) >>> m.rank() Traceback (most recent call last): ... NotImplementedError: Echelon form not implemented over 'Ring of integers modulo 4'.
- rescale_col(i, s, start_row=0)[source]¶
Replace \(i\)-th col of
self
by \(s\) times \(i\)-th col ofself
.INPUT:
i
– \(i\)-th columns
– scalarstart_row
– only rescale entries at this row and lower
EXAMPLES: We rescale the last column of a matrix over the rational numbers:
sage: a = matrix(QQ, 2, 3, range(6)); a [0 1 2] [3 4 5] sage: a.rescale_col(2, 1/2); a [ 0 1 1] [ 3 4 5/2] sage: R.<x> = QQ[]
>>> from sage.all import * >>> a = matrix(QQ, Integer(2), Integer(3), range(Integer(6))); a [0 1 2] [3 4 5] >>> a.rescale_col(Integer(2), Integer(1)/Integer(2)); a [ 0 1 1] [ 3 4 5/2] >>> R = QQ['x']; (x,) = R._first_ngens(1)
We rescale the last column of a matrix over a polynomial ring:
sage: a = matrix(R, 2, 3, [1,x,x^2,x^3,x^4,x^5]); a [ 1 x x^2] [x^3 x^4 x^5] sage: a.rescale_col(2, 1/2); a [ 1 x 1/2*x^2] [ x^3 x^4 1/2*x^5]
>>> from sage.all import * >>> a = matrix(R, Integer(2), Integer(3), [Integer(1),x,x**Integer(2),x**Integer(3),x**Integer(4),x**Integer(5)]); a [ 1 x x^2] [x^3 x^4 x^5] >>> a.rescale_col(Integer(2), Integer(1)/Integer(2)); a [ 1 x 1/2*x^2] [ x^3 x^4 1/2*x^5]
We try and fail to rescale a matrix over the integers by a non-integer:
sage: a = matrix(ZZ, 2, 3, [0,1,2, 3,4,4]); a [0 1 2] [3 4 4] sage: a.rescale_col(2, 1/2) Traceback (most recent call last): ... TypeError: Rescaling column by Rational Field element cannot be done over Integer Ring, use change_ring or with_rescaled_col instead.
>>> from sage.all import * >>> a = matrix(ZZ, Integer(2), Integer(3), [Integer(0),Integer(1),Integer(2), Integer(3),Integer(4),Integer(4)]); a [0 1 2] [3 4 4] >>> a.rescale_col(Integer(2), Integer(1)/Integer(2)) Traceback (most recent call last): ... TypeError: Rescaling column by Rational Field element cannot be done over Integer Ring, use change_ring or with_rescaled_col instead.
To rescale the matrix by 1/2, you must change the base ring to the rationals:
sage: a = a.change_ring(QQ); a [0 1 2] [3 4 4] sage: a.rescale_col(2,1/2); a [0 1 1] [3 4 2]
>>> from sage.all import * >>> a = a.change_ring(QQ); a [0 1 2] [3 4 4] >>> a.rescale_col(Integer(2),Integer(1)/Integer(2)); a [0 1 1] [3 4 2]
- rescale_row(i, s, start_col=0)[source]¶
Replace \(i\)-th row of
self
by \(s\) times \(i\)-th row ofself
.INPUT:
i
– \(i\)-th rows
– scalarstart_col
– only rescale entries at this column and to the right
EXAMPLES: We rescale the second row of a matrix over the rational numbers:
sage: a = matrix(QQ, 3, range(6)); a [0 1] [2 3] [4 5] sage: a.rescale_row(1, 1/2); a [ 0 1] [ 1 3/2] [ 4 5]
>>> from sage.all import * >>> a = matrix(QQ, Integer(3), range(Integer(6))); a [0 1] [2 3] [4 5] >>> a.rescale_row(Integer(1), Integer(1)/Integer(2)); a [ 0 1] [ 1 3/2] [ 4 5]
We rescale the second row of a matrix over a polynomial ring:
sage: R.<x> = QQ[] sage: a = matrix(R, 3, [1,x,x^2,x^3,x^4,x^5]); a [ 1 x] [x^2 x^3] [x^4 x^5] sage: a.rescale_row(1, 1/2); a [ 1 x] [1/2*x^2 1/2*x^3] [ x^4 x^5]
>>> from sage.all import * >>> R = QQ['x']; (x,) = R._first_ngens(1) >>> a = matrix(R, Integer(3), [Integer(1),x,x**Integer(2),x**Integer(3),x**Integer(4),x**Integer(5)]); a [ 1 x] [x^2 x^3] [x^4 x^5] >>> a.rescale_row(Integer(1), Integer(1)/Integer(2)); a [ 1 x] [1/2*x^2 1/2*x^3] [ x^4 x^5]
We try and fail to rescale a matrix over the integers by a non-integer:
sage: a = matrix(ZZ, 2, 3, [0,1,2, 3,4,4]); a [0 1 2] [3 4 4] sage: a.rescale_row(1, 1/2) Traceback (most recent call last): ... TypeError: Rescaling row by Rational Field element cannot be done over Integer Ring, use change_ring or with_rescaled_row instead.
>>> from sage.all import * >>> a = matrix(ZZ, Integer(2), Integer(3), [Integer(0),Integer(1),Integer(2), Integer(3),Integer(4),Integer(4)]); a [0 1 2] [3 4 4] >>> a.rescale_row(Integer(1), Integer(1)/Integer(2)) Traceback (most recent call last): ... TypeError: Rescaling row by Rational Field element cannot be done over Integer Ring, use change_ring or with_rescaled_row instead.
To rescale the matrix by 1/2, you must change the base ring to the rationals:
sage: a = a.change_ring(QQ); a [0 1 2] [3 4 4] sage: a.rescale_col(1, 1/2); a [ 0 1/2 2] [ 3 2 4]
>>> from sage.all import * >>> a = a.change_ring(QQ); a [0 1 2] [3 4 4] >>> a.rescale_col(Integer(1), Integer(1)/Integer(2)); a [ 0 1/2 2] [ 3 2 4]
- reverse_rows_and_columns()[source]¶
Reverse the row order and column order of this matrix.
This method transforms a matrix \(m_{i,j}\) with \(0 \leq i < nrows\) and \(0 \leq j < ncols\) into \(m_{nrows - i - 1, ncols - j - 1}\).
EXAMPLES:
sage: m = matrix(ZZ, 2, 2, range(4)) sage: m.reverse_rows_and_columns() sage: m [3 2] [1 0] sage: m = matrix(ZZ, 2, 3, range(6), sparse=True) sage: m.reverse_rows_and_columns() sage: m [5 4 3] [2 1 0] sage: m = matrix(ZZ, 3, 2, range(6), sparse=True) sage: m.reverse_rows_and_columns() sage: m [5 4] [3 2] [1 0] sage: m.reverse_rows_and_columns() sage: m [0 1] [2 3] [4 5] sage: m = matrix(QQ, 3, 2, [1/i for i in range(1,7)]) sage: m.reverse_rows_and_columns() sage: m [1/6 1/5] [1/4 1/3] [1/2 1] sage: R.<x,y> = ZZ['x,y'] sage: m = matrix(R, 3, 3, lambda i,j: x**i*y**j, sparse=True) sage: m.reverse_rows_and_columns() sage: m [x^2*y^2 x^2*y x^2] [ x*y^2 x*y x] [ y^2 y 1]
>>> from sage.all import * >>> m = matrix(ZZ, Integer(2), Integer(2), range(Integer(4))) >>> m.reverse_rows_and_columns() >>> m [3 2] [1 0] >>> m = matrix(ZZ, Integer(2), Integer(3), range(Integer(6)), sparse=True) >>> m.reverse_rows_and_columns() >>> m [5 4 3] [2 1 0] >>> m = matrix(ZZ, Integer(3), Integer(2), range(Integer(6)), sparse=True) >>> m.reverse_rows_and_columns() >>> m [5 4] [3 2] [1 0] >>> m.reverse_rows_and_columns() >>> m [0 1] [2 3] [4 5] >>> m = matrix(QQ, Integer(3), Integer(2), [Integer(1)/i for i in range(Integer(1),Integer(7))]) >>> m.reverse_rows_and_columns() >>> m [1/6 1/5] [1/4 1/3] [1/2 1] >>> R = ZZ['x,y']; (x, y,) = R._first_ngens(2) >>> m = matrix(R, Integer(3), Integer(3), lambda i,j: x**i*y**j, sparse=True) >>> m.reverse_rows_and_columns() >>> m [x^2*y^2 x^2*y x^2] [ x*y^2 x*y x] [ y^2 y 1]
If the matrix is immutable, the method raises an error:
sage: m = matrix(ZZ, 2, [1, 3, -2, 4]) sage: m.set_immutable() sage: m.reverse_rows_and_columns() Traceback (most recent call last): ... ValueError: matrix is immutable; please change a copy instead (i.e., use copy(M) to change a copy of M).
>>> from sage.all import * >>> m = matrix(ZZ, Integer(2), [Integer(1), Integer(3), -Integer(2), Integer(4)]) >>> m.set_immutable() >>> m.reverse_rows_and_columns() Traceback (most recent call last): ... ValueError: matrix is immutable; please change a copy instead (i.e., use copy(M) to change a copy of M).
- set_col_to_multiple_of_col(i, j, s)[source]¶
Set column i equal to s times column j.
EXAMPLES: We change the second column to -3 times the first column.
sage: a = matrix(ZZ, 2, 3, range(6)); a [0 1 2] [3 4 5] sage: a.set_col_to_multiple_of_col(1, 0, -3) sage: a [ 0 0 2] [ 3 -9 5]
>>> from sage.all import * >>> a = matrix(ZZ, Integer(2), Integer(3), range(Integer(6))); a [0 1 2] [3 4 5] >>> a.set_col_to_multiple_of_col(Integer(1), Integer(0), -Integer(3)) >>> a [ 0 0 2] [ 3 -9 5]
If we try to multiply a column by a rational number, we get an error message:
sage: a.set_col_to_multiple_of_col(1, 0, 1/2) Traceback (most recent call last): ... TypeError: Multiplying column by Rational Field element cannot be done over Integer Ring, use change_ring or with_col_set_to_multiple_of_col instead.
>>> from sage.all import * >>> a.set_col_to_multiple_of_col(Integer(1), Integer(0), Integer(1)/Integer(2)) Traceback (most recent call last): ... TypeError: Multiplying column by Rational Field element cannot be done over Integer Ring, use change_ring or with_col_set_to_multiple_of_col instead.
- set_immutable()[source]¶
Call this function to set the matrix as immutable.
Matrices are always mutable by default, i.e., you can change their entries using
A[i,j] = x
. However, mutable matrices aren’t hashable, so can’t be used as keys in dictionaries, etc. Also, often when implementing a class, you might compute a matrix associated to it, e.g., the matrix of a Hecke operator. If you return this matrix to the user you’re really returning a reference and the user could then change an entry; this could be confusing. Thus you should set such a matrix immutable.EXAMPLES:
sage: A = Matrix(QQ, 2, 2, range(4)) sage: A.is_mutable() True sage: A[0,0] = 10 sage: A [10 1] [ 2 3]
>>> from sage.all import * >>> A = Matrix(QQ, Integer(2), Integer(2), range(Integer(4))) >>> A.is_mutable() True >>> A[Integer(0),Integer(0)] = Integer(10) >>> A [10 1] [ 2 3]
Mutable matrices are not hashable, so can’t be used as keys for dictionaries:
sage: hash(A) Traceback (most recent call last): ... TypeError: mutable matrices are unhashable sage: v = {A:1} Traceback (most recent call last): ... TypeError: mutable matrices are unhashable
>>> from sage.all import * >>> hash(A) Traceback (most recent call last): ... TypeError: mutable matrices are unhashable >>> v = {A:Integer(1)} Traceback (most recent call last): ... TypeError: mutable matrices are unhashable
If we make A immutable it suddenly is hashable.
sage: A.set_immutable() sage: A.is_mutable() False sage: A[0,0] = 10 Traceback (most recent call last): ... ValueError: matrix is immutable; please change a copy instead (i.e., use copy(M) to change a copy of M). sage: hash(A) #random 12 sage: v = {A:1}; v {[10 1] [ 2 3]: 1}
>>> from sage.all import * >>> A.set_immutable() >>> A.is_mutable() False >>> A[Integer(0),Integer(0)] = Integer(10) Traceback (most recent call last): ... ValueError: matrix is immutable; please change a copy instead (i.e., use copy(M) to change a copy of M). >>> hash(A) #random 12 >>> v = {A:Integer(1)}; v {[10 1] [ 2 3]: 1}
- set_row_to_multiple_of_row(i, j, s)[source]¶
Set row i equal to s times row j.
EXAMPLES: We change the second row to -3 times the first row:
sage: a = matrix(ZZ, 2, 3, range(6)); a [0 1 2] [3 4 5] sage: a.set_row_to_multiple_of_row(1, 0, -3) sage: a [ 0 1 2] [ 0 -3 -6]
>>> from sage.all import * >>> a = matrix(ZZ, Integer(2), Integer(3), range(Integer(6))); a [0 1 2] [3 4 5] >>> a.set_row_to_multiple_of_row(Integer(1), Integer(0), -Integer(3)) >>> a [ 0 1 2] [ 0 -3 -6]
If we try to multiply a row by a rational number, we get an error message:
sage: a.set_row_to_multiple_of_row(1, 0, 1/2) Traceback (most recent call last): ... TypeError: Multiplying row by Rational Field element cannot be done over Integer Ring, use change_ring or with_row_set_to_multiple_of_row instead.
>>> from sage.all import * >>> a.set_row_to_multiple_of_row(Integer(1), Integer(0), Integer(1)/Integer(2)) Traceback (most recent call last): ... TypeError: Multiplying row by Rational Field element cannot be done over Integer Ring, use change_ring or with_row_set_to_multiple_of_row instead.
- str(rep_mapping=None, zero=None, plus_one=None, minus_one=None, unicode=False, shape=None, character_art=False, left_border=None, right_border=None, top_border=None, bottom_border=None)[source]¶
Return a nice string representation of the matrix.
INPUT:
rep_mapping
– dictionary or callable used to override the usual representation of elementsIf
rep_mapping
is a dictionary then keys should be elements of the base ring and values the desired string representation. Values sent in via the other keyword arguments will override values in the dictionary. Use of a dictionary can potentially take a very long time due to the need to hash entries of the matrix. Matrices with entries fromQQbar
are one example.If
rep_mapping
is callable then it will be called with elements of the matrix and must return a string. Simply callrepr()
on elements which should have the default representation.zero
– string (default:None
); if notNone
use the value ofzero
as the representation of the zero element.plus_one
– string (default:None
); if notNone
use the value ofplus_one
as the representation of the one element.minus_one
– string (default:None
); if notNone
use the value ofminus_one
as the representation of the negative of the one element.unicode
– boolean (default:False
); whether to use Unicode symbols instead of ASCII symbols for brackets and subdivision linesshape
– one of'square'
or'round'
(default:None
). Switches between round and square brackets. The default depends on the setting of theunicode
keyword argument. For Unicode symbols, the default is round brackets in accordance with the TeX rendering, while the ASCII rendering defaults to square brackets.character_art
– boolean (default:False
); ifTrue
, the result will be of typeAsciiArt
orUnicodeArt
which support line breaking of wide matrices that exceed the window widthleft_border
,right_border
– sequence (default:None
); if notNone
, callstr()
on the elements and use the results as labels for the rows of the matrix. The labels appear outside of the parentheses.top_border
,bottom_border
– sequence (default:None
); if notNone
, callstr()
on the elements and use the results as labels for the columns of the matrix. The labels appear outside of the parentheses.
EXAMPLES:
sage: R = PolynomialRing(QQ,6,'z') sage: a = matrix(2,3, R.gens()) sage: a.__repr__() '[z0 z1 z2]\n[z3 z4 z5]' sage: M = matrix([[1,0],[2,-1]]) sage: M.str() '[ 1 0]\n[ 2 -1]' sage: M.str(plus_one='+',minus_one='-',zero='.') '[+ .]\n[2 -]' sage: M.str({1:"not this one",2:"II"},minus_one='*',plus_one='I') '[ I 0]\n[II *]' sage: def print_entry(x): ....: if x>0: ....: return '+' ....: elif x<0: ....: return '-' ....: else: return '.' ... sage: M.str(print_entry) '[+ .]\n[+ -]' sage: M.str(repr) '[ 1 0]\n[ 2 -1]' sage: M = matrix([[1,2,3],[4,5,6],[7,8,9]]) sage: M.subdivide(None, 2) sage: print(M.str(unicode=True)) ⎛1 2│3⎞ ⎜4 5│6⎟ ⎝7 8│9⎠ sage: M.subdivide([0,1,1,3], [0,2,3,3]) sage: print(M.str(unicode=True, shape='square')) ⎡┼───┼─┼┼⎤ ⎢│1 2│3││⎥ ⎢┼───┼─┼┼⎥ ⎢┼───┼─┼┼⎥ ⎢│4 5│6││⎥ ⎢│7 8│9││⎥ ⎣┼───┼─┼┼⎦
>>> from sage.all import * >>> R = PolynomialRing(QQ,Integer(6),'z') >>> a = matrix(Integer(2),Integer(3), R.gens()) >>> a.__repr__() '[z0 z1 z2]\n[z3 z4 z5]' >>> M = matrix([[Integer(1),Integer(0)],[Integer(2),-Integer(1)]]) >>> M.str() '[ 1 0]\n[ 2 -1]' >>> M.str(plus_one='+',minus_one='-',zero='.') '[+ .]\n[2 -]' >>> M.str({Integer(1):"not this one",Integer(2):"II"},minus_one='*',plus_one='I') '[ I 0]\n[II *]' >>> def print_entry(x): ... if x>Integer(0): ... return '+' ... elif x<Integer(0): ... return '-' ... else: return '.' ... >>> M.str(print_entry) '[+ .]\n[+ -]' >>> M.str(repr) '[ 1 0]\n[ 2 -1]' >>> M = matrix([[Integer(1),Integer(2),Integer(3)],[Integer(4),Integer(5),Integer(6)],[Integer(7),Integer(8),Integer(9)]]) >>> M.subdivide(None, Integer(2)) >>> print(M.str(unicode=True)) ⎛1 2│3⎞ ⎜4 5│6⎟ ⎝7 8│9⎠ >>> M.subdivide([Integer(0),Integer(1),Integer(1),Integer(3)], [Integer(0),Integer(2),Integer(3),Integer(3)]) >>> print(M.str(unicode=True, shape='square')) ⎡┼───┼─┼┼⎤ ⎢│1 2│3││⎥ ⎢┼───┼─┼┼⎥ ⎢┼───┼─┼┼⎥ ⎢│4 5│6││⎥ ⎢│7 8│9││⎥ ⎣┼───┼─┼┼⎦
If
character_art
is set, the lines of large matrices are wrapped in a readable way:sage: set_random_seed(0) sage: matrix.random(RDF, 3, 5).str(unicode=True, character_art=True) ⎛ -0.27440062056807446 0.5031965950979831 -0.001975438590219314 ⎜ -0.05461130074681608 -0.033673314214051286 -0.9401270875197381 ⎝ 0.19906256610645512 0.3242250183948632 0.6026443545751128 -0.9467802263760512 0.5056889961514748⎞ -0.35104242112828943 0.5084492941557279⎟ -0.9541798283979341 -0.8948790563276592⎠
>>> from sage.all import * >>> set_random_seed(Integer(0)) >>> matrix.random(RDF, Integer(3), Integer(5)).str(unicode=True, character_art=True) ⎛ -0.27440062056807446 0.5031965950979831 -0.001975438590219314 ⎜ -0.05461130074681608 -0.033673314214051286 -0.9401270875197381 ⎝ 0.19906256610645512 0.3242250183948632 0.6026443545751128 <BLANKLINE> -0.9467802263760512 0.5056889961514748⎞ -0.35104242112828943 0.5084492941557279⎟ -0.9541798283979341 -0.8948790563276592⎠
The number of floating point digits to display is controlled by
matrix.options.precision
and can also be set by the IPython magic%precision
. This does not affect the internal precision of the represented data, but only the textual display of matrices:sage: matrix.options.precision = 4 sage: A = matrix(RR, [[1/3, 200/3], [-3, 1e6]]); A [ 0.3333 66.67] [ -3.000 1.000E+6] sage: unicode_art(A) ⎛ 0.3333 66.67⎞ ⎝ -3.000 1.000E+6⎠ sage: matrix.options.precision = None sage: A [ 0.333333333333333 66.6666666666667] [ -3.00000000000000 1.00000000000000e6]
>>> from sage.all import * >>> matrix.options.precision = Integer(4) >>> A = matrix(RR, [[Integer(1)/Integer(3), Integer(200)/Integer(3)], [-Integer(3), RealNumber('1e6')]]); A [ 0.3333 66.67] [ -3.000 1.000E+6] >>> unicode_art(A) ⎛ 0.3333 66.67⎞ ⎝ -3.000 1.000E+6⎠ >>> matrix.options.precision = None >>> A [ 0.333333333333333 66.6666666666667] [ -3.00000000000000 1.00000000000000e6]
Matrices with borders:
sage: M = matrix([[1,2,3], [4,5,6], [7,8,9]]) sage: M.subdivide(None, 2) sage: print(M.str(unicode=True, ....: top_border=['ab', 'cde', 'f'], ....: bottom_border=['*', '', ''], ....: left_border=[1, 10, 100], ....: right_border=['', ' <', ''])) ab cde f 1⎛ 1 2│ 3⎞ 10⎜ 4 5│ 6⎟ < 100⎝ 7 8│ 9⎠ *
>>> from sage.all import * >>> M = matrix([[Integer(1),Integer(2),Integer(3)], [Integer(4),Integer(5),Integer(6)], [Integer(7),Integer(8),Integer(9)]]) >>> M.subdivide(None, Integer(2)) >>> print(M.str(unicode=True, ... top_border=['ab', 'cde', 'f'], ... bottom_border=['*', '', ''], ... left_border=[Integer(1), Integer(10), Integer(100)], ... right_border=['', ' <', ''])) ab cde f 1⎛ 1 2│ 3⎞ 10⎜ 4 5│ 6⎟ < 100⎝ 7 8│ 9⎠ *
- swap_columns(c1, c2)[source]¶
Swap columns c1 and c2 of
self
.EXAMPLES: We create a rational matrix:
sage: M = MatrixSpace(QQ,3,3) sage: A = M([1,9,-7,4/5,4,3,6,4,3]) sage: A [ 1 9 -7] [4/5 4 3] [ 6 4 3]
>>> from sage.all import * >>> M = MatrixSpace(QQ,Integer(3),Integer(3)) >>> A = M([Integer(1),Integer(9),-Integer(7),Integer(4)/Integer(5),Integer(4),Integer(3),Integer(6),Integer(4),Integer(3)]) >>> A [ 1 9 -7] [4/5 4 3] [ 6 4 3]
Since the first column is numbered zero, this swaps the second and third columns:
sage: A.swap_columns(1,2); A [ 1 -7 9] [4/5 3 4] [ 6 3 4]
>>> from sage.all import * >>> A.swap_columns(Integer(1),Integer(2)); A [ 1 -7 9] [4/5 3 4] [ 6 3 4]
- swap_rows(r1, r2)[source]¶
Swap rows r1 and r2 of
self
.EXAMPLES: We create a rational matrix:
sage: M = MatrixSpace(QQ, 3, 3) sage: A = M([1,9,-7, 4/5,4,3, 6,4,3]) sage: A [ 1 9 -7] [4/5 4 3] [ 6 4 3]
>>> from sage.all import * >>> M = MatrixSpace(QQ, Integer(3), Integer(3)) >>> A = M([Integer(1),Integer(9),-Integer(7), Integer(4)/Integer(5),Integer(4),Integer(3), Integer(6),Integer(4),Integer(3)]) >>> A [ 1 9 -7] [4/5 4 3] [ 6 4 3]
Since the first row is numbered zero, this swaps the first and third rows:
sage: A.swap_rows(0, 2); A [ 6 4 3] [4/5 4 3] [ 1 9 -7]
>>> from sage.all import * >>> A.swap_rows(Integer(0), Integer(2)); A [ 6 4 3] [4/5 4 3] [ 1 9 -7]
- with_added_multiple_of_column(i, j, s, start_row=0)[source]¶
Add s times column j to column i, returning new matrix.
EXAMPLES: We add -1 times the third column to the second column of an integer matrix, remembering to start numbering cols at zero:
sage: a = matrix(ZZ, 2, 3, range(6)); a [0 1 2] [3 4 5] sage: b = a.with_added_multiple_of_column(1, 2, -1); b [ 0 -1 2] [ 3 -1 5]
>>> from sage.all import * >>> a = matrix(ZZ, Integer(2), Integer(3), range(Integer(6))); a [0 1 2] [3 4 5] >>> b = a.with_added_multiple_of_column(Integer(1), Integer(2), -Integer(1)); b [ 0 -1 2] [ 3 -1 5]
The original matrix is unchanged:
sage: a [0 1 2] [3 4 5]
>>> from sage.all import * >>> a [0 1 2] [3 4 5]
Adding a rational multiple is okay, and reassigning a variable is okay:
sage: a = a.with_added_multiple_of_column(0, 1, 1/3); a [ 1/3 1 2] [13/3 4 5]
>>> from sage.all import * >>> a = a.with_added_multiple_of_column(Integer(0), Integer(1), Integer(1)/Integer(3)); a [ 1/3 1 2] [13/3 4 5]
- with_added_multiple_of_row(i, j, s, start_col=0)[source]¶
Add s times row j to row i, returning new matrix.
EXAMPLES: We add -3 times the first row to the second row of an integer matrix, remembering to start numbering rows at zero:
sage: a = matrix(ZZ,2,3,range(6)); a [0 1 2] [3 4 5] sage: b = a.with_added_multiple_of_row(1,0,-3); b [ 0 1 2] [ 3 1 -1]
>>> from sage.all import * >>> a = matrix(ZZ,Integer(2),Integer(3),range(Integer(6))); a [0 1 2] [3 4 5] >>> b = a.with_added_multiple_of_row(Integer(1),Integer(0),-Integer(3)); b [ 0 1 2] [ 3 1 -1]
The original matrix is unchanged:
sage: a [0 1 2] [3 4 5]
>>> from sage.all import * >>> a [0 1 2] [3 4 5]
Adding a rational multiple is okay, and reassigning a variable is okay:
sage: a = a.with_added_multiple_of_row(0,1,1/3); a [ 1 7/3 11/3] [ 3 4 5]
>>> from sage.all import * >>> a = a.with_added_multiple_of_row(Integer(0),Integer(1),Integer(1)/Integer(3)); a [ 1 7/3 11/3] [ 3 4 5]
- with_col_set_to_multiple_of_col(i, j, s)[source]¶
Set column i equal to s times column j, returning a new matrix.
EXAMPLES: We change the second column to -3 times the first column.
sage: a = matrix(ZZ, 2, 3, range(6)); a [0 1 2] [3 4 5] sage: b = a.with_col_set_to_multiple_of_col(1, 0, -3); b [ 0 0 2] [ 3 -9 5]
>>> from sage.all import * >>> a = matrix(ZZ, Integer(2), Integer(3), range(Integer(6))); a [0 1 2] [3 4 5] >>> b = a.with_col_set_to_multiple_of_col(Integer(1), Integer(0), -Integer(3)); b [ 0 0 2] [ 3 -9 5]
Note that the original matrix is unchanged:
sage: a [0 1 2] [3 4 5]
>>> from sage.all import * >>> a [0 1 2] [3 4 5]
Adding a rational multiple is okay, and reassigning a variable is okay:
sage: a = a.with_col_set_to_multiple_of_col(1, 0, 1/2); a [ 0 0 2] [ 3 3/2 5]
>>> from sage.all import * >>> a = a.with_col_set_to_multiple_of_col(Integer(1), Integer(0), Integer(1)/Integer(2)); a [ 0 0 2] [ 3 3/2 5]
- with_permuted_columns(permutation)[source]¶
Return the matrix obtained from permuting the columns of
self
by applying the permutation group elementpermutation
.As permutation group elements act on integers \(\{1,\dots,n\}\), columns are considered numbered from 1 for this operation.
INPUT:
permutation
– aPermutationGroupElement
OUTPUT: a matrix
EXAMPLES: We create some matrix:
sage: M = matrix(ZZ, [[1,0,0,0,0],[0,2,0,0,0],[0,0,3,0,0],[0,0,0,4,0],[0,0,0,0,5]]) sage: M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
>>> from sage.all import * >>> M = matrix(ZZ, [[Integer(1),Integer(0),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(2),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(3),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(4),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(0),Integer(5)]]) >>> M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
Next of all, create a permutation group element and act on
M
:sage: # needs sage.groups sage: G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) sage: sigma, tau = G.gens() sage: sigma (1,2,3)(4,5) sage: M.with_permuted_columns(sigma) [0 0 1 0 0] [2 0 0 0 0] [0 3 0 0 0] [0 0 0 0 4] [0 0 0 5 0]
>>> from sage.all import * >>> # needs sage.groups >>> G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) >>> sigma, tau = G.gens() >>> sigma (1,2,3)(4,5) >>> M.with_permuted_columns(sigma) [0 0 1 0 0] [2 0 0 0 0] [0 3 0 0 0] [0 0 0 0 4] [0 0 0 5 0]
- with_permuted_rows(permutation)[source]¶
Return the matrix obtained from permuting the rows of
self
by applying the permutation group elementpermutation
.As permutation group elements act on integers \(\{1,\dots,n\}\), rows are considered numbered from 1 for this operation.
INPUT:
permutation
– aPermutationGroupElement
OUTPUT: a matrix
EXAMPLES: We create a matrix:
sage: M = matrix(ZZ, [[1,0,0,0,0],[0,2,0,0,0],[0,0,3,0,0],[0,0,0,4,0],[0,0,0,0,5]]) sage: M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
>>> from sage.all import * >>> M = matrix(ZZ, [[Integer(1),Integer(0),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(2),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(3),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(4),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(0),Integer(5)]]) >>> M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
Next of all, create a permutation group element and act on
M
:sage: # needs sage.groups sage: G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) sage: sigma, tau = G.gens() sage: sigma (1,2,3)(4,5) sage: M.with_permuted_rows(sigma) [0 2 0 0 0] [0 0 3 0 0] [1 0 0 0 0] [0 0 0 0 5] [0 0 0 4 0]
>>> from sage.all import * >>> # needs sage.groups >>> G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) >>> sigma, tau = G.gens() >>> sigma (1,2,3)(4,5) >>> M.with_permuted_rows(sigma) [0 2 0 0 0] [0 0 3 0 0] [1 0 0 0 0] [0 0 0 0 5] [0 0 0 4 0]
- with_permuted_rows_and_columns(row_permutation, column_permutation)[source]¶
Return the matrix obtained from permuting the rows and columns of
self
by applying the permutation group elementsrow_permutation
andcolumn_permutation
.As permutation group elements act on integers \(\{1,\dots,n\}\), rows and columns are considered numbered from 1 for this operation.
INPUT:
row_permutation
– aPermutationGroupElement
column_permutation
– aPermutationGroupElement
OUTPUT: a matrix
EXAMPLES: We create a matrix:
sage: M = matrix(ZZ, [[1,0,0,0,0],[0,2,0,0,0],[0,0,3,0,0],[0,0,0,4,0],[0,0,0,0,5]]) sage: M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
>>> from sage.all import * >>> M = matrix(ZZ, [[Integer(1),Integer(0),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(2),Integer(0),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(3),Integer(0),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(4),Integer(0)],[Integer(0),Integer(0),Integer(0),Integer(0),Integer(5)]]) >>> M [1 0 0 0 0] [0 2 0 0 0] [0 0 3 0 0] [0 0 0 4 0] [0 0 0 0 5]
Next of all, create a permutation group element and act on
M
:sage: # needs sage.groups sage: G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) sage: sigma, tau = G.gens() sage: sigma (1,2,3)(4,5) sage: M.with_permuted_rows_and_columns(sigma,tau) [2 0 0 0 0] [0 3 0 0 0] [0 0 0 0 1] [0 0 0 5 0] [0 0 4 0 0]
>>> from sage.all import * >>> # needs sage.groups >>> G = PermutationGroup(['(1,2,3)(4,5)', '(1,2,3,4,5)']) >>> sigma, tau = G.gens() >>> sigma (1,2,3)(4,5) >>> M.with_permuted_rows_and_columns(sigma,tau) [2 0 0 0 0] [0 3 0 0 0] [0 0 0 0 1] [0 0 0 5 0] [0 0 4 0 0]
- with_rescaled_col(i, s, start_row=0)[source]¶
Replaces \(i\)-th col of
self
by \(s\) times \(i\)-th col of self, returning new matrix.EXAMPLES: We rescale the last column of a matrix over the integers:
sage: a = matrix(ZZ, 2, 3, range(6)); a [0 1 2] [3 4 5] sage: b = a.with_rescaled_col(2, -2); b [ 0 1 -4] [ 3 4 -10]
>>> from sage.all import * >>> a = matrix(ZZ, Integer(2), Integer(3), range(Integer(6))); a [0 1 2] [3 4 5] >>> b = a.with_rescaled_col(Integer(2), -Integer(2)); b [ 0 1 -4] [ 3 4 -10]
The original matrix is unchanged:
sage: a [0 1 2] [3 4 5]
>>> from sage.all import * >>> a [0 1 2] [3 4 5]
Adding a rational multiple is okay, and reassigning a variable is okay:
sage: a = a.with_rescaled_col(1, 1/3); a [ 0 1/3 2] [ 3 4/3 5]
>>> from sage.all import * >>> a = a.with_rescaled_col(Integer(1), Integer(1)/Integer(3)); a [ 0 1/3 2] [ 3 4/3 5]
- with_rescaled_row(i, s, start_col=0)[source]¶
Replace \(i\)-th row of
self
by s times \(i\)-th row of self, returning new matrix.EXAMPLES: We rescale the second row of a matrix over the integers:
sage: a = matrix(ZZ, 3, 2, range(6)); a [0 1] [2 3] [4 5] sage: b = a.with_rescaled_row(1, -2); b [ 0 1] [-4 -6] [ 4 5]
>>> from sage.all import * >>> a = matrix(ZZ, Integer(3), Integer(2), range(Integer(6))); a [0 1] [2 3] [4 5] >>> b = a.with_rescaled_row(Integer(1), -Integer(2)); b [ 0 1] [-4 -6] [ 4 5]
The original matrix is unchanged:
sage: a [0 1] [2 3] [4 5]
>>> from sage.all import * >>> a [0 1] [2 3] [4 5]
Adding a rational multiple is okay, and reassigning a variable is okay:
sage: a = a.with_rescaled_row(2, 1/3); a [ 0 1] [ 2 3] [4/3 5/3]
>>> from sage.all import * >>> a = a.with_rescaled_row(Integer(2), Integer(1)/Integer(3)); a [ 0 1] [ 2 3] [4/3 5/3]
- with_row_set_to_multiple_of_row(i, j, s)[source]¶
Set row i equal to s times row j, returning a new matrix.
EXAMPLES: We change the second row to -3 times the first row:
sage: a = matrix(ZZ, 2, 3, range(6)); a [0 1 2] [3 4 5] sage: b = a.with_row_set_to_multiple_of_row(1, 0, -3); b [ 0 1 2] [ 0 -3 -6]
>>> from sage.all import * >>> a = matrix(ZZ, Integer(2), Integer(3), range(Integer(6))); a [0 1 2] [3 4 5] >>> b = a.with_row_set_to_multiple_of_row(Integer(1), Integer(0), -Integer(3)); b [ 0 1 2] [ 0 -3 -6]
Note that the original matrix is unchanged:
sage: a [0 1 2] [3 4 5]
>>> from sage.all import * >>> a [0 1 2] [3 4 5]
Adding a rational multiple is okay, and reassigning a variable is okay:
sage: a = a.with_row_set_to_multiple_of_row(1, 0, 1/2); a [ 0 1 2] [ 0 1/2 1]
>>> from sage.all import * >>> a = a.with_row_set_to_multiple_of_row(Integer(1), Integer(0), Integer(1)/Integer(2)); a [ 0 1 2] [ 0 1/2 1]
- with_swapped_columns(c1, c2)[source]¶
Swap columns
c1
andc2
ofself
and return a new matrix.INPUT:
c1
,c2
– integers specifying columns ofself
to interchange
OUTPUT:
A new matrix, identical to
self
except that columnsc1
andc2
are swapped.EXAMPLES:
Remember that columns are numbered starting from zero.
sage: A = matrix(QQ, 4, range(20)) sage: A.with_swapped_columns(1, 2) [ 0 2 1 3 4] [ 5 7 6 8 9] [10 12 11 13 14] [15 17 16 18 19]
>>> from sage.all import * >>> A = matrix(QQ, Integer(4), range(Integer(20))) >>> A.with_swapped_columns(Integer(1), Integer(2)) [ 0 2 1 3 4] [ 5 7 6 8 9] [10 12 11 13 14] [15 17 16 18 19]
Trying to swap a column with itself will succeed, but still return a new matrix.
sage: A = matrix(QQ, 4, range(20)) sage: B = A.with_swapped_columns(2, 2) sage: A == B True sage: A is B False
>>> from sage.all import * >>> A = matrix(QQ, Integer(4), range(Integer(20))) >>> B = A.with_swapped_columns(Integer(2), Integer(2)) >>> A == B True >>> A is B False
The column specifications are checked.
sage: A = matrix(4, range(20)) sage: A.with_swapped_columns(-1, 2) Traceback (most recent call last): ... IndexError: matrix column index out of range sage: A.with_swapped_columns(2, 5) Traceback (most recent call last): ... IndexError: matrix column index out of range
>>> from sage.all import * >>> A = matrix(Integer(4), range(Integer(20))) >>> A.with_swapped_columns(-Integer(1), Integer(2)) Traceback (most recent call last): ... IndexError: matrix column index out of range >>> A.with_swapped_columns(Integer(2), Integer(5)) Traceback (most recent call last): ... IndexError: matrix column index out of range
- with_swapped_rows(r1, r2)[source]¶
Swap rows
r1
andr2
ofself
and return a new matrix.INPUT:
r1
,r2
– integers specifying rows ofself
to interchange
OUTPUT:
A new matrix, identical to
self
except that rowsr1
andr2
are swapped.EXAMPLES:
Remember that rows are numbered starting from zero.
sage: A = matrix(QQ, 4, range(20)) sage: A.with_swapped_rows(1, 2) [ 0 1 2 3 4] [10 11 12 13 14] [ 5 6 7 8 9] [15 16 17 18 19]
>>> from sage.all import * >>> A = matrix(QQ, Integer(4), range(Integer(20))) >>> A.with_swapped_rows(Integer(1), Integer(2)) [ 0 1 2 3 4] [10 11 12 13 14] [ 5 6 7 8 9] [15 16 17 18 19]
Trying to swap a row with itself will succeed, but still return a new matrix.
sage: A = matrix(QQ, 4, range(20)) sage: B = A.with_swapped_rows(2, 2) sage: A == B True sage: A is B False
>>> from sage.all import * >>> A = matrix(QQ, Integer(4), range(Integer(20))) >>> B = A.with_swapped_rows(Integer(2), Integer(2)) >>> A == B True >>> A is B False
The row specifications are checked.
sage: A = matrix(4, range(20)) sage: A.with_swapped_rows(-1, 2) Traceback (most recent call last): ... IndexError: matrix row index out of range sage: A.with_swapped_rows(2, 5) Traceback (most recent call last): ... IndexError: matrix row index out of range
>>> from sage.all import * >>> A = matrix(Integer(4), range(Integer(20))) >>> A.with_swapped_rows(-Integer(1), Integer(2)) Traceback (most recent call last): ... IndexError: matrix row index out of range >>> A.with_swapped_rows(Integer(2), Integer(5)) Traceback (most recent call last): ... IndexError: matrix row index out of range
- sage.matrix.matrix0.set_max_cols(n)[source]¶
Set the global variable
max_cols
(which is used in deciding how to output a matrix).EXAMPLES:
sage: from sage.matrix.matrix0 import set_max_cols sage: set_max_cols(50) doctest:...: DeprecationWarning: 'set_max_cols' is replaced by 'matrix.options.max_cols' See https://github.com/sagemath/sage/issues/30552 for details.
>>> from sage.all import * >>> from sage.matrix.matrix0 import set_max_cols >>> set_max_cols(Integer(50)) doctest:...: DeprecationWarning: 'set_max_cols' is replaced by 'matrix.options.max_cols' See https://github.com/sagemath/sage/issues/30552 for details.
- sage.matrix.matrix0.set_max_rows(n)[source]¶
Set the global variable
max_rows
(which is used in deciding how to output a matrix).EXAMPLES:
sage: from sage.matrix.matrix0 import set_max_rows sage: set_max_rows(20) doctest:...: DeprecationWarning: 'set_max_rows' is replaced by 'matrix.options.max_rows' See https://github.com/sagemath/sage/issues/30552 for details.
>>> from sage.all import * >>> from sage.matrix.matrix0 import set_max_rows >>> set_max_rows(Integer(20)) doctest:...: DeprecationWarning: 'set_max_rows' is replaced by 'matrix.options.max_rows' See https://github.com/sagemath/sage/issues/30552 for details.
- sage.matrix.matrix0.unpickle(cls, parent, immutability, cache, data, version)[source]¶
Unpickle a matrix. This is only used internally by Sage. Users should never call this function directly.
EXAMPLES: We illustrating saving and loading several different types of matrices.
OVER \(\ZZ\):
sage: A = matrix(ZZ, 2, range(4)) sage: loads(dumps(A)) # indirect doctest [0 1] [2 3]
>>> from sage.all import * >>> A = matrix(ZZ, Integer(2), range(Integer(4))) >>> loads(dumps(A)) # indirect doctest [0 1] [2 3]
Sparse OVER \(\QQ\):
Dense over \(\QQ[x,y]\):
Dense over finite field.