Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
sagemath
GitHub Repository: sagemath/sagesmc
Path: blob/master/src/sage/matrix/matrix0.pyx
8815 views
1
"""
2
Base class for matrices, part 0
3
4
.. note::
5
6
For design documentation see matrix/docs.py.
7
8
EXAMPLES::
9
10
sage: matrix(2,[1,2,3,4])
11
[1 2]
12
[3 4]
13
"""
14
15
################################################################################
16
# Copyright (C) 2005, 2006 William Stein <[email protected]>
17
#
18
# Distributed under the terms of the GNU General Public License (GPL).
19
# The full text of the GPL is available at:
20
#
21
# http://www.gnu.org/licenses/
22
################################################################################
23
24
include "sage/ext/stdsage.pxi"
25
include "sage/ext/cdefs.pxi"
26
include "sage/ext/python.pxi"
27
from cpython.list cimport *
28
from cpython.object cimport *
29
include "sage/ext/python_slice.pxi"
30
from cpython.tuple cimport *
31
32
import sage.modules.free_module
33
import sage.misc.latex
34
import sage.rings.integer
35
36
from sage.misc.misc import verbose, get_verbose
37
from sage.structure.sequence import Sequence
38
39
cimport sage.structure.element
40
from sage.structure.element cimport ModuleElement, Element, RingElement, Vector
41
from sage.structure.mutability cimport Mutability
42
from sage.misc.misc_c cimport normalize_index
43
44
from sage.rings.ring cimport CommutativeRing
45
from sage.rings.ring import is_Ring
46
from sage.rings.finite_rings.integer_mod_ring import is_IntegerModRing
47
48
import sage.modules.free_module
49
50
import matrix_misc
51
52
cdef extern from "Python.h":
53
bint PySlice_Check(PyObject* ob)
54
55
cdef class Matrix(sage.structure.element.Matrix):
56
r"""
57
A generic matrix.
58
59
The ``Matrix`` class is the base class for all matrix
60
classes. To create a ``Matrix``, first create a
61
``MatrixSpace``, then coerce a list of elements into
62
the ``MatrixSpace``. See the documentation of
63
``MatrixSpace`` for more details.
64
65
EXAMPLES:
66
67
We illustrate matrices and matrix spaces. Note that no actual
68
matrix that you make should have class Matrix; the class should
69
always be derived from Matrix.
70
71
::
72
73
sage: M = MatrixSpace(CDF,2,3); M
74
Full MatrixSpace of 2 by 3 dense matrices over Complex Double Field
75
sage: a = M([1,2,3, 4,5,6]); a
76
[1.0 2.0 3.0]
77
[4.0 5.0 6.0]
78
sage: type(a)
79
<type 'sage.matrix.matrix_complex_double_dense.Matrix_complex_double_dense'>
80
sage: parent(a)
81
Full MatrixSpace of 2 by 3 dense matrices over Complex Double Field
82
83
::
84
85
sage: matrix(CDF, 2,3, [1,2,3, 4,5,6])
86
[1.0 2.0 3.0]
87
[4.0 5.0 6.0]
88
sage: Mat(CDF,2,3)(range(1,7))
89
[1.0 2.0 3.0]
90
[4.0 5.0 6.0]
91
92
::
93
94
sage: Q.<i,j,k> = QuaternionAlgebra(QQ, -1,-1)
95
sage: matrix(Q,2,1,[1,2])
96
[1]
97
[2]
98
"""
99
def __init__(self, parent):
100
"""
101
The initialization routine of the Matrix base class ensures that it sets
102
the attributes self._parent, self._base_ring, self._nrows, self._ncols.
103
It sets the latter ones by accessing the relevant information on parent,
104
which is often slower than what a more specific subclass can do.
105
106
Subclasses of Matrix can safely skip calling Matrix.__init__ provided they
107
take care of initializing these attributes themselves.
108
109
The private attributes self._is_immutable and self._cache are implicitly
110
initialized to valid values upon memory allocation.
111
112
EXAMPLES::
113
114
sage: import sage.matrix.matrix0
115
sage: A = sage.matrix.matrix0.Matrix(MatrixSpace(QQ,2))
116
sage: type(A)
117
<type 'sage.matrix.matrix0.Matrix'>
118
"""
119
self._parent = parent
120
self._base_ring = parent.base_ring()
121
self._nrows = parent.nrows()
122
self._ncols = parent.ncols()
123
124
def list(self):
125
"""
126
List of the elements of self ordered by elements in each
127
row. It is safe to change the returned list.
128
129
.. warning::
130
131
This function returns a list of the entries in the matrix
132
self. It does not return a list of the rows of self, so it
133
is different than the output of list(self), which returns
134
``[self[0],self[1],...]``.
135
136
EXAMPLES::
137
138
sage: R.<x,y> = QQ[]
139
sage: a = matrix(R,2,[x,y,x*y, y,x,2*x+y]); a
140
[ x y x*y]
141
[ y x 2*x + y]
142
sage: v = a.list(); v
143
[x, y, x*y, y, x, 2*x + y]
144
145
Note that list(a) is different than a.list()::
146
147
sage: a.list()
148
[x, y, x*y, y, x, 2*x + y]
149
sage: list(a)
150
[(x, y, x*y), (y, x, 2*x + y)]
151
152
Notice that changing the returned list does not change a (the list
153
is a copy)::
154
155
sage: v[0] = 25
156
sage: a
157
[ x y x*y]
158
[ y x 2*x + y]
159
"""
160
return list(self._list())
161
162
def _list(self):
163
"""
164
Unsafe version of the list method, mainly for internal use. This
165
may return the list of elements, but as an *unsafe* reference to
166
the underlying list of the object. It is might be dangerous if you
167
change entries of the returned list.
168
169
EXAMPLES: Using _list is potentially fast and memory efficient,
170
but very dangerous (at least for generic dense matrices).
171
172
::
173
174
sage: a = matrix(QQ['x,y'],2,range(6)); a
175
[0 1 2]
176
[3 4 5]
177
sage: v = a._list(); v
178
[0, 1, 2, 3, 4, 5]
179
180
If you change an entry of the list, the corresponding entry of the
181
matrix will be changed (but without clearing any caches of
182
computing information about the matrix)::
183
184
sage: v[0] = -2/3; v
185
[-2/3, 1, 2, 3, 4, 5]
186
sage: a._list()
187
[-2/3, 1, 2, 3, 4, 5]
188
189
Now the 0,0 entry of the matrix is `-2/3`, which is weird.
190
191
::
192
193
sage: a[0,0]
194
-2/3
195
196
See::
197
198
sage: a
199
[-2/3 1 2]
200
[ 3 4 5]
201
"""
202
cdef Py_ssize_t i, j
203
204
x = self.fetch('list')
205
if not x is None:
206
return x
207
x = []
208
for i from 0 <= i < self._nrows:
209
for j from 0 <= j < self._ncols:
210
x.append(self.get_unsafe(i, j))
211
return x
212
213
def dict(self):
214
"""
215
Dictionary of the elements of self with keys pairs (i,j) and values
216
the nonzero entries of self.
217
218
It is safe to change the returned dictionary.
219
220
EXAMPLES::
221
222
sage: R.<x,y> = QQ[]
223
sage: a = matrix(R,2,[x,y,0, 0,0,2*x+y]); a
224
[ x y 0]
225
[ 0 0 2*x + y]
226
sage: d = a.dict(); d
227
{(0, 1): y, (1, 2): 2*x + y, (0, 0): x}
228
229
Notice that changing the returned list does not change a (the list
230
is a copy)::
231
232
sage: d[0,0] = 25
233
sage: a
234
[ x y 0]
235
[ 0 0 2*x + y]
236
"""
237
return dict(self._dict())
238
239
def _dict(self):
240
"""
241
Unsafe version of the dict method, mainly for internal use.
242
This may return the dict of elements, but as an *unsafe*
243
reference to the underlying dict of the object. It might
244
dangerous if you change entries of the returned dict.
245
246
EXAMPLES: Using _dict is potentially fast and memory efficient,
247
but very dangerous (at least for generic sparse matrices).
248
249
::
250
251
sage: a = matrix(QQ['x,y'],2,range(6), sparse=True); a
252
[0 1 2]
253
[3 4 5]
254
sage: v = a._dict(); v
255
{(0, 1): 1, (1, 2): 5, (1, 0): 3, (0, 2): 2, (1, 1): 4}
256
257
If you change a key of the dictionary, the corresponding entry of
258
the matrix will be changed (but without clearing any caches of
259
computing information about the matrix)::
260
261
sage: v[0,1] = -2/3; v
262
{(0, 1): -2/3, (1, 2): 5, (1, 0): 3, (0, 2): 2, (1, 1): 4}
263
sage: a._dict()
264
{(0, 1): -2/3, (1, 2): 5, (1, 0): 3, (0, 2): 2, (1, 1): 4}
265
sage: a[0,1]
266
-2/3
267
268
But the matrix doesn't know the entry changed, so it returns the
269
cached version of its print representation::
270
271
sage: a
272
[0 1 2]
273
[3 4 5]
274
275
If we change an entry, the cache is cleared, and the correct print
276
representation appears::
277
278
sage: a[1,2]=10
279
sage: a
280
[ 0 -2/3 2]
281
[ 3 4 10]
282
"""
283
d = self.fetch('dict')
284
if not d is None:
285
return d
286
287
cdef Py_ssize_t i, j
288
d = {}
289
for i from 0 <= i < self._nrows:
290
for j from 0 <= j < self._ncols:
291
x = self.get_unsafe(i, j)
292
if x != 0:
293
d[(int(i),int(j))] = x
294
self.cache('dict', d)
295
return d
296
297
###########################################################
298
# Cache
299
###########################################################
300
def _clear_cache(self):
301
"""
302
Clear anything cached about this matrix.
303
304
EXAMPLES::
305
306
sage: m=Matrix(QQ,2,range(0,4))
307
sage: m._clear_cache()
308
309
"""
310
self.clear_cache()
311
312
cdef clear_cache(self):
313
"""
314
Clear the properties cache.
315
"""
316
self._cache = None
317
318
cdef fetch(self, key):
319
"""
320
Try to get an element from the cache; if there isn't anything
321
there, return None.
322
"""
323
if self._cache is None:
324
return None
325
try:
326
return self._cache[key]
327
except KeyError:
328
return None
329
330
cdef cache(self, key, x):
331
"""
332
Record x in the cache with given key.
333
"""
334
if self._cache is None:
335
self._cache = {}
336
self._cache[key] = x
337
338
def _get_cache(self):
339
"""
340
Return the cache.
341
342
EXAMPLES::
343
344
sage: m=Matrix(QQ,2,range(0,4))
345
sage: m._get_cache()
346
{}
347
348
"""
349
if self._cache is None:
350
self._cache = {}
351
return self._cache
352
353
###########################################################
354
# Mutability and bounds checking
355
###########################################################
356
357
cdef check_bounds(self, Py_ssize_t i, Py_ssize_t j):
358
"""
359
This function gets called when you're about to access the i,j entry
360
of this matrix. If i, j are out of range, an IndexError is
361
raised.
362
"""
363
if i<0 or i >= self._nrows or j<0 or j >= self._ncols:
364
raise IndexError("matrix index out of range")
365
366
cdef check_mutability(self):
367
"""
368
This function gets called when you're about to change this matrix.
369
370
If self is immutable, a ValueError is raised, since you should
371
never change a mutable matrix.
372
373
If self is mutable, the cache of results about self is deleted.
374
"""
375
if self._is_immutable:
376
raise ValueError("matrix is immutable; please change a copy instead (i.e., use copy(M) to change a copy of M).")
377
else:
378
self._cache = None
379
380
cdef check_bounds_and_mutability(self, Py_ssize_t i, Py_ssize_t j):
381
"""
382
This function gets called when you're about to set the i,j entry of
383
this matrix. If i or j is out of range, an IndexError exception is
384
raised.
385
386
If self is immutable, a ValueError is raised, since you should
387
never change a mutable matrix.
388
389
If self is mutable, the cache of results about self is deleted.
390
"""
391
if self._is_immutable:
392
raise ValueError("matrix is immutable; please change a copy instead (i.e., use copy(M) to change a copy of M).")
393
else:
394
self._cache = None
395
396
if i<0 or i >= self._nrows or j<0 or j >= self._ncols:
397
raise IndexError("matrix index out of range")
398
399
def set_immutable(self):
400
r"""
401
Call this function to set the matrix as immutable.
402
403
Matrices are always mutable by default, i.e., you can change their
404
entries using ``A[i,j] = x``. However, mutable matrices
405
aren't hashable, so can't be used as keys in dictionaries, etc.
406
Also, often when implementing a class, you might compute a matrix
407
associated to it, e.g., the matrix of a Hecke operator. If you
408
return this matrix to the user you're really returning a reference
409
and the user could then change an entry; this could be confusing.
410
Thus you should set such a matrix immutable.
411
412
EXAMPLES::
413
414
sage: A = Matrix(QQ, 2, 2, range(4))
415
sage: A.is_mutable()
416
True
417
sage: A[0,0] = 10
418
sage: A
419
[10 1]
420
[ 2 3]
421
422
Mutable matrices are not hashable, so can't be used as keys for
423
dictionaries::
424
425
sage: hash(A)
426
Traceback (most recent call last):
427
...
428
TypeError: mutable matrices are unhashable
429
sage: v = {A:1}
430
Traceback (most recent call last):
431
...
432
TypeError: mutable matrices are unhashable
433
434
If we make A immutable it suddenly is hashable.
435
436
::
437
438
sage: A.set_immutable()
439
sage: A.is_mutable()
440
False
441
sage: A[0,0] = 10
442
Traceback (most recent call last):
443
...
444
ValueError: matrix is immutable; please change a copy instead (i.e., use copy(M) to change a copy of M).
445
sage: hash(A) #random
446
12
447
sage: v = {A:1}; v
448
{[10 1]
449
[ 2 3]: 1}
450
"""
451
self._is_immutable = True
452
453
def is_immutable(self):
454
"""
455
Return True if this matrix is immutable.
456
457
See the documentation for self.set_immutable for more details
458
about mutability.
459
460
EXAMPLES::
461
462
sage: A = Matrix(QQ['t','s'], 2, 2, range(4))
463
sage: A.is_immutable()
464
False
465
sage: A.set_immutable()
466
sage: A.is_immutable()
467
True
468
"""
469
return self._is_immutable
470
471
def is_mutable(self):
472
"""
473
Return True if this matrix is mutable.
474
475
See the documentation for self.set_immutable for more details
476
about mutability.
477
478
EXAMPLES::
479
480
sage: A = Matrix(QQ['t','s'], 2, 2, range(4))
481
sage: A.is_mutable()
482
True
483
sage: A.set_immutable()
484
sage: A.is_mutable()
485
False
486
"""
487
return not(self._is_immutable)
488
489
###########################################################
490
# Entry access
491
# The first two must be overloaded in the derived class
492
###########################################################
493
cdef set_unsafe(self, Py_ssize_t i, Py_ssize_t j, object x):
494
"""
495
Set entry quickly without doing any bounds checking. Calling this
496
with invalid arguments is allowed to produce a segmentation fault.
497
498
This is fast since it is a cdef function and there is no bounds
499
checking.
500
"""
501
raise NotImplementedError("this must be defined in the derived class (type=%s)"%type(self))
502
503
cdef get_unsafe(self, Py_ssize_t i, Py_ssize_t j):
504
"""
505
Entry access, but fast since it might be without bounds checking.
506
507
This is fast since it is a cdef function and there is no bounds
508
checking.
509
"""
510
raise NotImplementedError("this must be defined in the derived type.")
511
512
## def _get_very_unsafe(self, i, j):
513
## r"""
514
## Entry access, but potentially fast since it might be without
515
## bounds checking. (I know of no cases where this is actually
516
## faster.)
517
518
## This function it can very easily !! SEG FAULT !! if you call
519
## it with invalid input. Use with *extreme* caution.
520
521
## EXAMPLES:
522
## sage: a = matrix(ZZ,2,range(4))
523
## sage: a._get_very_unsafe(0,1)
524
## 1
525
526
## If you do \code{a.\_get\_very\_unsafe(0,10)} you'll very likely crash Sage
527
## completely.
528
## """
529
## return self.get_unsafe(i, j)
530
531
def __iter__(self):
532
"""
533
Return an iterator for the rows of self
534
535
EXAMPLES::
536
537
sage: m=matrix(2,[1,2,3,4])
538
sage: m.__iter__().next()
539
(1, 2)
540
"""
541
542
return matrix_misc.row_iterator(self)
543
544
def __getitem__(self, key):
545
"""
546
Return element, row, or slice of self.
547
548
INPUT:
549
550
- ``key``- tuple (i,j) where i, j can be integers, slices or lists
551
552
USAGE:
553
554
- ``A[i, j]`` - the i,j element (or elements, if i or j are
555
slices or lists) of A, or
556
557
- ``A[i:j]`` - rows of A, according to slice notation
558
559
EXAMPLES::
560
561
sage: A = Matrix(Integers(2006),2,2,[-1,2,3,4])
562
sage: A[0,0]
563
2005
564
sage: A[0]
565
(2005, 2)
566
567
The returned row is immutable (mainly to avoid confusion)::
568
569
sage: A[0][0] = 123
570
Traceback (most recent call last):
571
...
572
ValueError: vector is immutable; please change a copy instead (use copy())
573
sage: A[0].is_immutable()
574
True
575
sage: a = matrix(ZZ,3,range(9)); a
576
[0 1 2]
577
[3 4 5]
578
[6 7 8]
579
sage: a[1,2]
580
5
581
sage: a[0]
582
(0, 1, 2)
583
sage: a[4,7]
584
Traceback (most recent call last):
585
...
586
IndexError: matrix index out of range
587
sage: a[-1,0]
588
6
589
590
::
591
592
sage: a[2.7]
593
Traceback (most recent call last):
594
...
595
TypeError: index must be an integer
596
sage: a[1, 2.7]
597
Traceback (most recent call last):
598
...
599
TypeError: index must be an integer
600
sage: a[2.7, 1]
601
Traceback (most recent call last):
602
...
603
TypeError: index must be an integer
604
605
sage: m=[(1, -2, -1, -1,9), (1, 8, 6, 2,2), (1, 1, -1, 1,4), (-1, 2, -2, -1,4)];M= matrix(m)
606
sage: M
607
[ 1 -2 -1 -1 9]
608
[ 1 8 6 2 2]
609
[ 1 1 -1 1 4]
610
[-1 2 -2 -1 4]
611
612
Get the 2 x 2 submatrix of M, starting at row index and column
613
index 1
614
615
::
616
617
sage: M[1:3,1:3]
618
[ 8 6]
619
[ 1 -1]
620
621
Get the 2 x 3 submatrix of M starting at row index and column index
622
1::
623
624
sage: M[1:3,[1..3]]
625
[ 8 6 2]
626
[ 1 -1 1]
627
628
Get the second column of M::
629
630
sage: M[:,1]
631
[-2]
632
[ 8]
633
[ 1]
634
[ 2]
635
636
Get the first row of M::
637
638
sage: M[0,:]
639
[ 1 -2 -1 -1 9]
640
641
More examples::
642
643
sage: M[range(2),:]
644
[ 1 -2 -1 -1 9]
645
[ 1 8 6 2 2]
646
sage: M[range(2),4]
647
[9]
648
[2]
649
sage: M[range(3),range(5)]
650
[ 1 -2 -1 -1 9]
651
[ 1 8 6 2 2]
652
[ 1 1 -1 1 4]
653
654
::
655
656
sage: M[3,range(5)]
657
[-1 2 -2 -1 4]
658
sage: M[3,:]
659
[-1 2 -2 -1 4]
660
sage: M[3,4]
661
4
662
663
sage: M[-1,:]
664
[-1 2 -2 -1 4]
665
666
sage: A = matrix(ZZ,3,4, [3, 2, -5, 0, 1, -1, 1, -4, 1, 0, 1, -3]); A
667
[ 3 2 -5 0]
668
[ 1 -1 1 -4]
669
[ 1 0 1 -3]
670
671
::
672
673
sage: A[:,0:4:2]
674
[ 3 -5]
675
[ 1 1]
676
[ 1 1]
677
678
::
679
680
sage: A[1:,0:4:2]
681
[1 1]
682
[1 1]
683
684
sage: A[2::-1,:]
685
[ 1 0 1 -3]
686
[ 1 -1 1 -4]
687
[ 3 2 -5 0]
688
689
sage: A[1:,3::-1]
690
[-4 1 -1 1]
691
[-3 1 0 1]
692
693
sage: A[1:,3::-2]
694
[-4 -1]
695
[-3 0]
696
697
sage: A[2::-1,3:1:-1]
698
[-3 1]
699
[-4 1]
700
[ 0 -5]
701
702
::
703
704
sage: A= matrix(3,4,[1, 0, -3, -1, 3, 0, -2, 1, -3, -5, -1, -5])
705
sage: A[range(2,-1,-1),:]
706
[-3 -5 -1 -5]
707
[ 3 0 -2 1]
708
[ 1 0 -3 -1]
709
710
::
711
712
sage: A[range(2,-1,-1),range(3,-1,-1)]
713
[-5 -1 -5 -3]
714
[ 1 -2 0 3]
715
[-1 -3 0 1]
716
717
::
718
719
sage: A = matrix(2, [1, 2, 3, 4])
720
sage: A[[0,0],[0,0]]
721
[1 1]
722
[1 1]
723
724
::
725
726
sage: M = matrix(3, 4, range(12))
727
sage: M[0:0, 0:0]
728
[]
729
sage: M[0:0, 1:4]
730
[]
731
sage: M[2:3, 3:3]
732
[]
733
sage: M[range(2,2), :3]
734
[]
735
sage: M[(1,2), 3]
736
[ 7]
737
[11]
738
sage: M[(1,2),(0,1,1)]
739
[4 5 5]
740
[8 9 9]
741
sage: m=[(1, -2, -1, -1), (1, 8, 6, 2), (1, 1, -1, 1), (-1, 2, -2, -1)]
742
sage: M= matrix(m);M
743
[ 1 -2 -1 -1]
744
[ 1 8 6 2]
745
[ 1 1 -1 1]
746
[-1 2 -2 -1]
747
748
sage: M[:2]
749
[ 1 -2 -1 -1]
750
[ 1 8 6 2]
751
sage: M[:]
752
[ 1 -2 -1 -1]
753
[ 1 8 6 2]
754
[ 1 1 -1 1]
755
[-1 2 -2 -1]
756
sage: M[1:3]
757
[ 1 8 6 2]
758
[ 1 1 -1 1]
759
760
sage: A=matrix(QQ,10,range(100))
761
sage: A[0:3]
762
[ 0 1 2 3 4 5 6 7 8 9]
763
[10 11 12 13 14 15 16 17 18 19]
764
[20 21 22 23 24 25 26 27 28 29]
765
sage: A[:2]
766
[ 0 1 2 3 4 5 6 7 8 9]
767
[10 11 12 13 14 15 16 17 18 19]
768
sage: A[8:]
769
[80 81 82 83 84 85 86 87 88 89]
770
[90 91 92 93 94 95 96 97 98 99]
771
sage: A[1:10:3]
772
[10 11 12 13 14 15 16 17 18 19]
773
[40 41 42 43 44 45 46 47 48 49]
774
[70 71 72 73 74 75 76 77 78 79]
775
sage: A[-1]
776
(90, 91, 92, 93, 94, 95, 96, 97, 98, 99)
777
sage: A[-1:-6:-2]
778
[90 91 92 93 94 95 96 97 98 99]
779
[70 71 72 73 74 75 76 77 78 79]
780
[50 51 52 53 54 55 56 57 58 59]
781
782
sage: A[3].is_immutable()
783
True
784
sage: A[1:3].is_immutable()
785
True
786
787
Slices that result in zero rows or zero columns are supported too::
788
789
sage: m = identity_matrix(QQ, 4)[4:,:]
790
sage: m.nrows(), m.ncols()
791
(0, 4)
792
sage: m * vector(QQ, 4)
793
()
794
795
TESTS:
796
797
If we're given lists as arguments, we should throw an
798
appropriate error when those lists do not contain valid
799
indices (trac #6569)::
800
801
sage: A = matrix(4, range(1,17))
802
sage: A[[1.5], [1]]
803
Traceback (most recent call last):
804
...
805
IndexError: row indices must be integers
806
sage: A[[1], [1.5]]
807
Traceback (most recent call last):
808
...
809
IndexError: column indices must be integers
810
sage: A[[1.5]]
811
Traceback (most recent call last):
812
...
813
IndexError: row indices must be integers
814
815
Before trac #6569 was fixed, sparse/dense matrices behaved
816
differently due to implementation details. Given invalid
817
indices, they should fail in the same manner. These tests
818
just repeat the previous set with a sparse matrix::
819
820
sage: A = matrix(4, range(1,17), sparse=True)
821
sage: A[[1.5], [1]]
822
Traceback (most recent call last):
823
...
824
IndexError: row indices must be integers
825
sage: A[[1], [1.5]]
826
Traceback (most recent call last):
827
...
828
IndexError: column indices must be integers
829
sage: A[[1.5]]
830
Traceback (most recent call last):
831
...
832
IndexError: row indices must be integers
833
834
"""
835
cdef list row_list
836
cdef list col_list
837
cdef Py_ssize_t i
838
cdef int row, col
839
cdef int nrows = self._nrows
840
cdef int ncols = self._ncols
841
cdef tuple key_tuple
842
cdef object row_index, col_index
843
cdef int ind
844
845
# used to keep track of when an index is a
846
# single number
847
cdef int single_row = 0, single_col = 0
848
849
if PyTuple_CheckExact(key):
850
key_tuple = <tuple>key
851
#if PyTuple_Size(key_tuple) != 2:
852
if len(key_tuple) != 2:
853
raise IndexError("index must be an integer or pair of integers")
854
855
row_index = <object>PyTuple_GET_ITEM(key_tuple, 0)
856
col_index = <object>PyTuple_GET_ITEM(key_tuple, 1)
857
858
if PyList_CheckExact(row_index) or PyTuple_CheckExact(row_index):
859
if PyTuple_CheckExact(row_index):
860
row_list = list(row_index)
861
else:
862
row_list = row_index
863
864
for i from 0 <= i < len(row_list):
865
# The 'ind' variable is 'cdef int' and will
866
# truncate a float to a valid index. So, we have
867
# to test row_list[i] instead.
868
if not PyIndex_Check(row_list[i]):
869
raise IndexError('row indices must be integers')
870
871
ind = row_list[i]
872
if ind < 0:
873
ind += nrows
874
row_list[i] = ind
875
876
if ind < 0 or ind >= nrows:
877
raise IndexError("matrix index out of range")
878
elif PySlice_Check(<PyObject *>row_index):
879
row_list = range(*row_index.indices(nrows))
880
else:
881
if not PyIndex_Check(row_index):
882
raise TypeError("index must be an integer")
883
row = row_index
884
if row < 0:
885
row += nrows
886
if row < 0 or row >= nrows:
887
raise IndexError("matrix index out of range")
888
single_row = 1
889
890
if PyList_CheckExact(col_index) or PyTuple_CheckExact(col_index):
891
if PyTuple_CheckExact(col_index):
892
col_list = list(col_index)
893
else:
894
col_list = col_index
895
896
for i from 0 <= i < len(col_list):
897
# The 'ind' variable is 'cdef int' and will
898
# truncate a float to a valid index. So, we have
899
# to test col_list[i] instead.
900
if not PyIndex_Check(col_list[i]):
901
raise IndexError('column indices must be integers')
902
903
ind = col_list[i]
904
if ind < 0:
905
ind += ncols
906
col_list[i] = ind
907
908
if ind < 0 or ind >= ncols:
909
raise IndexError("matrix index out of range")
910
elif PySlice_Check(<PyObject *>col_index):
911
col_list = range(*col_index.indices(ncols))
912
else:
913
if not PyIndex_Check(col_index):
914
raise TypeError("index must be an integer")
915
col = col_index
916
if col < 0:
917
col += ncols
918
if col < 0 or col >= ncols:
919
raise IndexError("matrix index out of range")
920
single_col = 1
921
922
# if we had a single row entry and a single column entry,
923
# we want to just do a get_unsafe
924
if single_row and single_col:
925
return self.get_unsafe(row, col)
926
927
# otherwise, prep these for the call to
928
# matrix_from_rows_and_columns
929
if single_row:
930
row_list = [row]
931
if single_col:
932
col_list = [col]
933
934
if len(row_list) == 0 or len(col_list) == 0:
935
return self.new_matrix(nrows=len(row_list), ncols=len(col_list))
936
937
return self.matrix_from_rows_and_columns(row_list,col_list)
938
939
940
row_index = key
941
if PyList_CheckExact(row_index) or PyTuple_CheckExact(row_index):
942
if PyTuple_CheckExact(row_index):
943
row_list = list(row_index)
944
else:
945
row_list = row_index
946
947
for i from 0 <= i < len(row_list):
948
# The 'ind' variable is 'cdef int' and will
949
# truncate a float to a valid index. So, we have
950
# to test row_list[i] instead.
951
if not PyIndex_Check(row_list[i]):
952
raise IndexError('row indices must be integers')
953
954
ind = row_list[i]
955
if ind < 0:
956
ind += nrows
957
row_list[i] = ind
958
959
if ind < 0 or ind >= nrows:
960
raise IndexError("matrix index out of range")
961
r = self.matrix_from_rows(row_list)
962
elif PySlice_Check(<PyObject *>row_index):
963
row_list = range(*row_index.indices(nrows))
964
r = self.matrix_from_rows(row_list)
965
else:
966
if not PyIndex_Check(row_index):
967
raise TypeError("index must be an integer")
968
row = row_index
969
if row < 0:
970
row += nrows
971
if row < 0 or row >= nrows:
972
raise IndexError("matrix index out of range")
973
r = self.row(row)
974
975
r.set_immutable()
976
return r
977
978
def __setitem__(self, key, value):
979
"""
980
Set elements of this matrix to values given in value.
981
982
INPUT:
983
984
- ``key`` - any legal indexing (i.e., such that self[key] works)
985
986
- ``value`` - values that are used to set the elements indicated by key.
987
988
EXAMPLES::
989
990
sage: A = Matrix(Integers(2006),2,2,[-1,2,3,4])
991
sage: A[0,0]=43; A
992
[43 2]
993
[ 3 4]
994
995
sage: A[0]=[10,20]; A
996
[10 20]
997
[ 3 4]
998
999
sage: M=matrix([(1, -2, -1, -1,9), (1, 8, 6, 2,2), (1, 1, -1, 1,4), (-1, 2, -2, -1,4)]); M
1000
[ 1 -2 -1 -1 9]
1001
[ 1 8 6 2 2]
1002
[ 1 1 -1 1 4]
1003
[-1 2 -2 -1 4]
1004
1005
Set the 2 x 2 submatrix of M, starting at row index and column
1006
index 1::
1007
1008
sage: M[1:3,1:3] = [[1,0],[0,1]]; M
1009
[ 1 -2 -1 -1 9]
1010
[ 1 1 0 2 2]
1011
[ 1 0 1 1 4]
1012
[-1 2 -2 -1 4]
1013
1014
Set the 2 x 3 submatrix of M starting at row index and column
1015
index 1::
1016
1017
sage: M[1:3,[1..3]] = M[2:4,0:3]; M
1018
[ 1 -2 -1 -1 9]
1019
[ 1 1 0 1 2]
1020
[ 1 -1 2 -2 4]
1021
[-1 2 -2 -1 4]
1022
1023
Set part of the first column of M::
1024
1025
sage: M[1:,0]=[[2],[3],[4]]; M
1026
[ 1 -2 -1 -1 9]
1027
[ 2 1 0 1 2]
1028
[ 3 -1 2 -2 4]
1029
[ 4 2 -2 -1 4]
1030
1031
Or do a similar thing with a vector::
1032
1033
sage: M[1:,0]=vector([-2,-3,-4]); M
1034
[ 1 -2 -1 -1 9]
1035
[-2 1 0 1 2]
1036
[-3 -1 2 -2 4]
1037
[-4 2 -2 -1 4]
1038
1039
Or a constant::
1040
1041
sage: M[1:,0]=30; M
1042
[ 1 -2 -1 -1 9]
1043
[30 1 0 1 2]
1044
[30 -1 2 -2 4]
1045
[30 2 -2 -1 4]
1046
1047
1048
Set the first row of M::
1049
1050
sage: M[0,:]=[[20,21,22,23,24]]; M
1051
[20 21 22 23 24]
1052
[30 1 0 1 2]
1053
[30 -1 2 -2 4]
1054
[30 2 -2 -1 4]
1055
sage: M[0,:]=vector([0,1,2,3,4]); M
1056
[ 0 1 2 3 4]
1057
[30 1 0 1 2]
1058
[30 -1 2 -2 4]
1059
[30 2 -2 -1 4]
1060
sage: M[0,:]=-3; M
1061
[-3 -3 -3 -3 -3]
1062
[30 1 0 1 2]
1063
[30 -1 2 -2 4]
1064
[30 2 -2 -1 4]
1065
1066
1067
sage: A = matrix(ZZ,3,4, [3, 2, -5, 0, 1, -1, 1, -4, 1, 0, 1, -3]); A
1068
[ 3 2 -5 0]
1069
[ 1 -1 1 -4]
1070
[ 1 0 1 -3]
1071
1072
We can use the step feature of slices to set every other column::
1073
1074
sage: A[:,0:3:2] = 5; A
1075
[ 5 2 5 0]
1076
[ 5 -1 5 -4]
1077
[ 5 0 5 -3]
1078
1079
sage: A[1:,0:4:2] = [[100,200],[300,400]]; A
1080
[ 5 2 5 0]
1081
[100 -1 200 -4]
1082
[300 0 400 -3]
1083
1084
We can also count backwards to flip the matrix upside down.
1085
1086
::
1087
1088
sage: A[::-1,:]=A; A
1089
[300 0 400 -3]
1090
[100 -1 200 -4]
1091
[ 5 2 5 0]
1092
1093
1094
sage: A[1:,3::-1]=[[2,3,0,1],[9,8,7,6]]; A
1095
[300 0 400 -3]
1096
[ 1 0 3 2]
1097
[ 6 7 8 9]
1098
1099
sage: A[1:,::-2] = A[1:,::2]; A
1100
[300 0 400 -3]
1101
[ 1 3 3 1]
1102
[ 6 8 8 6]
1103
1104
sage: A[::-1,3:1:-1] = [[4,3],[1,2],[-1,-2]]; A
1105
[300 0 -2 -1]
1106
[ 1 3 2 1]
1107
[ 6 8 3 4]
1108
1109
1110
TESTS::
1111
1112
sage: A = MatrixSpace(ZZ,3)(range(9)); A
1113
[0 1 2]
1114
[3 4 5]
1115
[6 7 8]
1116
sage: A[1,2]=100; A
1117
[ 0 1 2]
1118
[ 3 4 100]
1119
[ 6 7 8]
1120
sage: A[0]=(10,20,30); A
1121
[ 10 20 30]
1122
[ 3 4 100]
1123
[ 6 7 8]
1124
sage: A[4,7]=45
1125
Traceback (most recent call last):
1126
...
1127
IndexError: index out of range
1128
sage: A[-1,0]=63; A[-1,0]
1129
63
1130
sage: A[2.7]=3
1131
Traceback (most recent call last):
1132
...
1133
TypeError: index must be an integer or slice or a tuple/list of integers and slices
1134
sage: A[1, 2.7]=3
1135
Traceback (most recent call last):
1136
...
1137
TypeError: index must be an integer or slice or a tuple/list of integers and slices
1138
sage: A[2.7, 1]=3
1139
Traceback (most recent call last):
1140
...
1141
TypeError: index must be an integer or slice or a tuple/list of integers and slices
1142
sage: A.set_immutable()
1143
sage: A[0,0] = 7
1144
Traceback (most recent call last):
1145
...
1146
ValueError: matrix is immutable; please change a copy instead (i.e., use copy(M) to change a copy of M).
1147
sage: A=matrix([[1,2],[3,4]]); B=matrix([[1,3],[5,7]])
1148
sage: A[1:2,1:2]=B[1:2,1:2]
1149
sage: A
1150
[1 2]
1151
[3 7]
1152
sage: A=matrix([[1,2],[3,4]]); B=matrix([[1,3],[5,7]])
1153
sage: A[1,0:1]=B[1,1:2]
1154
sage: A
1155
[1 2]
1156
[7 4]
1157
1158
1159
More examples::
1160
1161
sage: M[range(2),:]=[[1..5], [6..10]]; M
1162
[ 1 2 3 4 5]
1163
[ 6 7 8 9 10]
1164
[30 -1 2 -2 4]
1165
[30 2 -2 -1 4]
1166
1167
sage: M[range(2),4]=0; M
1168
[ 1 2 3 4 0]
1169
[ 6 7 8 9 0]
1170
[30 -1 2 -2 4]
1171
[30 2 -2 -1 4]
1172
1173
sage: M[range(3),range(5)]=M[range(1,4), :]; M
1174
[ 6 7 8 9 0]
1175
[30 -1 2 -2 4]
1176
[30 2 -2 -1 4]
1177
[30 2 -2 -1 4]
1178
1179
1180
sage: M[3,range(5)]=vector([-2,3,4,-5,4]); M
1181
[ 6 7 8 9 0]
1182
[30 -1 2 -2 4]
1183
[30 2 -2 -1 4]
1184
[-2 3 4 -5 4]
1185
sage: M[3,:]=2*M[2,:]; M
1186
[ 6 7 8 9 0]
1187
[30 -1 2 -2 4]
1188
[30 2 -2 -1 4]
1189
[60 4 -4 -2 8]
1190
sage: M[3,4]=M[3,2]; M
1191
[ 6 7 8 9 0]
1192
[30 -1 2 -2 4]
1193
[30 2 -2 -1 4]
1194
[60 4 -4 -2 -4]
1195
1196
sage: M[-1,:]=M[-3,:]; M
1197
[ 6 7 8 9 0]
1198
[30 -1 2 -2 4]
1199
[30 2 -2 -1 4]
1200
[30 -1 2 -2 4]
1201
1202
1203
sage: A= matrix(3,4,[1, 0, -3, -1, 3, 0, -2, 1, -3, -5, -1, -5]); A
1204
[ 1 0 -3 -1]
1205
[ 3 0 -2 1]
1206
[-3 -5 -1 -5]
1207
1208
sage: A[range(2,-1,-1),:]=A; A
1209
[-3 -5 -1 -5]
1210
[ 3 0 -2 1]
1211
[ 1 0 -3 -1]
1212
1213
sage: A[range(2,-1,-1),range(3,-1,-1)]=A; A
1214
[-1 -3 0 1]
1215
[ 1 -2 0 3]
1216
[-5 -1 -5 -3]
1217
1218
sage: A = matrix(2, [1, 2, 3, 4])
1219
sage: A[[0,0],[0,0]]=10; A
1220
[10 2]
1221
[ 3 4]
1222
1223
sage: M = matrix(3, 4, range(12))
1224
sage: M[0:0, 0:0]=20; M
1225
[ 0 1 2 3]
1226
[ 4 5 6 7]
1227
[ 8 9 10 11]
1228
sage: M[0:0, 1:4]=20; M
1229
[ 0 1 2 3]
1230
[ 4 5 6 7]
1231
[ 8 9 10 11]
1232
sage: M[2:3, 3:3]=20; M
1233
[ 0 1 2 3]
1234
[ 4 5 6 7]
1235
[ 8 9 10 11]
1236
sage: M[range(2,2), :3]=20; M
1237
[ 0 1 2 3]
1238
[ 4 5 6 7]
1239
[ 8 9 10 11]
1240
sage: M[(1,2), 3]=vector([-1,-2]); M
1241
[ 0 1 2 3]
1242
[ 4 5 6 -1]
1243
[ 8 9 10 -2]
1244
sage: M[(1,2),(0,1,1)]=[[-1,-2,-3],[-4,-5,-6]]; M
1245
[ 0 1 2 3]
1246
[-1 -3 6 -1]
1247
[-4 -6 10 -2]
1248
sage: M=matrix([(1, -2, -1, -1), (1, 8, 6, 2), (1, 1, -1, 1), (-1, 2, -2, -1)]); M
1249
[ 1 -2 -1 -1]
1250
[ 1 8 6 2]
1251
[ 1 1 -1 1]
1252
[-1 2 -2 -1]
1253
1254
sage: M[:2]=M[2:]; M
1255
[ 1 1 -1 1]
1256
[-1 2 -2 -1]
1257
[ 1 1 -1 1]
1258
[-1 2 -2 -1]
1259
1260
sage: M[:] = M.transpose(); M
1261
[ 1 -1 1 -1]
1262
[ 1 2 1 2]
1263
[-1 -2 -1 -2]
1264
[ 1 -1 1 -1]
1265
sage: M = matrix(ZZ,4,range(16)); M
1266
[ 0 1 2 3]
1267
[ 4 5 6 7]
1268
[ 8 9 10 11]
1269
[12 13 14 15]
1270
sage: M[::2]=M[::-2]; M
1271
[12 13 14 15]
1272
[ 4 5 6 7]
1273
[ 4 5 6 7]
1274
[12 13 14 15]
1275
sage: M[::2]=2; M
1276
[ 2 2 2 2]
1277
[ 4 5 6 7]
1278
[ 2 2 2 2]
1279
[12 13 14 15]
1280
1281
sage: M[2:]=10; M
1282
[ 2 2 2 2]
1283
[ 4 5 6 7]
1284
[10 10 10 10]
1285
[10 10 10 10]
1286
1287
sage: M=matrix(3,1,[1,2,3]); M
1288
[1]
1289
[2]
1290
[3]
1291
sage: M[1] = vector([20]); M
1292
[ 1]
1293
[20]
1294
[ 3]
1295
sage: M = matrix(3, 2, srange(6)); M[1] = 15; M
1296
[ 0 1]
1297
[15 15]
1298
[ 4 5]
1299
sage: M = matrix(3, 1, srange(3)); M[1] = 15; M
1300
[ 0]
1301
[15]
1302
[ 2]
1303
sage: M = matrix(3, 1, srange(3)); M[1] = [15]; M
1304
[ 0]
1305
[15]
1306
[ 2]
1307
"""
1308
cdef list row_list
1309
cdef list col_list
1310
cdef object index
1311
cdef Py_ssize_t row_list_len, col_list_len
1312
cdef list value_list
1313
cdef bint value_list_one_dimensional = 0
1314
cdef Py_ssize_t i
1315
cdef Py_ssize_t row, col
1316
cdef Py_ssize_t nrows = self._nrows
1317
cdef Py_ssize_t ncols = self._ncols
1318
cdef tuple key_tuple
1319
cdef object row_index, col_index
1320
cdef object value_row
1321
1322
# used to keep track of when an index is a
1323
# single number
1324
cdef bint single_row = 0, single_col = 0
1325
cdef bint no_col_index = 0
1326
1327
# If the matrix is immutable, check_mutability will raise an
1328
# exception.
1329
self.check_mutability()
1330
1331
if PyTuple_CheckExact(key):
1332
key_tuple = <tuple>key
1333
#if PyTuple_Size(key_tuple) != 2:
1334
if len(key_tuple) != 2:
1335
raise IndexError("index can't have more than two components")
1336
1337
row_index = <object>PyTuple_GET_ITEM(key_tuple, 0)
1338
col_index = <object>PyTuple_GET_ITEM(key_tuple, 1)
1339
1340
1341
if PyIndex_Check(col_index):
1342
col = col_index
1343
if col < 0:
1344
col += ncols
1345
if col < 0 or col >= ncols:
1346
raise IndexError("index out of range")
1347
single_col = 1
1348
col_list_len = 1
1349
else:
1350
col_list = normalize_index(col_index, ncols)
1351
col_list_len = len(col_list)
1352
if col_list_len==0:
1353
return
1354
1355
else:
1356
no_col_index = 1
1357
row_index = key
1358
col_list_len = ncols
1359
if col_list_len==0:
1360
return
1361
1362
# Special-case a single-row.
1363
if PyIndex_Check(row_index):
1364
row = row_index
1365
if row < 0:
1366
row += nrows
1367
if row < 0 or row >= nrows:
1368
raise IndexError("index out of range")
1369
single_row = 1
1370
row_list_len = 1
1371
else:
1372
row_list = normalize_index(row_index, nrows)
1373
row_list_len = len(row_list)
1374
if row_list_len==0:
1375
return
1376
1377
if single_row and single_col and not no_col_index:
1378
self.set_unsafe(row, col, self._coerce_element(value))
1379
return
1380
1381
if PyList_CheckExact(value):
1382
if single_row and no_col_index:
1383
# A convenience addition, so we can set a row by
1384
# M[1] = [1,2,3] or M[1,:]=[1,2,3]
1385
value_list_one_dimensional = 1
1386
value_list = value
1387
elif PyTuple_CheckExact(value):
1388
if single_row and no_col_index:
1389
# A convenience addition, so we can set a row by
1390
# M[1] = [1,2,3] or M[1,:]=[1,2,3]
1391
value_list_one_dimensional = 1
1392
value_list = list(value)
1393
elif IS_INSTANCE(value, Matrix):
1394
value_list = list(value)
1395
elif IS_INSTANCE(value, Vector):
1396
if single_row or single_col:
1397
value_list_one_dimensional = 1
1398
value_list = list(value)
1399
else:
1400
raise IndexError("value does not have the right dimensions")
1401
else:
1402
# If value is not a list, tuple, matrix, or vector, try
1403
# broadcasting the element to all positions.
1404
value_element = self._coerce_element(value)
1405
if single_row:
1406
if no_col_index:
1407
for col in range(col_list_len):
1408
self.set_unsafe(row, col, value_element)
1409
else:
1410
for col in col_list:
1411
self.set_unsafe(row, col, value_element)
1412
elif single_col:
1413
for row in row_list:
1414
self.set_unsafe(row, col, value_element)
1415
else:
1416
if no_col_index:
1417
for row in row_list:
1418
for col in range(col_list_len):
1419
self.set_unsafe(row, col, value_element)
1420
else:
1421
for row in row_list:
1422
for col in col_list:
1423
self.set_unsafe(row, col, value_element)
1424
return
1425
1426
if value_list_one_dimensional:
1427
# This will break when assigning a vector to a column
1428
if single_row and col_list_len != len(value_list):
1429
raise IndexError("value does not have the right number of columns")
1430
elif single_col and row_list_len != len(value_list):
1431
raise IndexError("value does not have the right number of rows")
1432
else:
1433
if row_list_len != len(value_list):
1434
raise IndexError("value does not have the right number of rows")
1435
for value_row in value_list:
1436
if col_list_len != len(value_row):
1437
raise IndexError("value does not have the right number of columns")
1438
1439
1440
if single_row:
1441
if value_list_one_dimensional:
1442
value_row = value_list
1443
else:
1444
value_row = value_list[0]
1445
1446
if no_col_index:
1447
for col in range(col_list_len):
1448
self.set_unsafe(row, col, self._coerce_element(value_row[col]))
1449
else:
1450
for col in range(col_list_len):
1451
self.set_unsafe(row, col_list[col], self._coerce_element(value_row[col]))
1452
elif single_col:
1453
if value_list_one_dimensional:
1454
for row in range(row_list_len):
1455
self.set_unsafe(row_list[row], col, self._coerce_element(value_list[row]))
1456
else:
1457
for row in range(row_list_len):
1458
self.set_unsafe(row_list[row], col, self._coerce_element(value_list[row][0]))
1459
else:
1460
if no_col_index:
1461
for i in range(row_list_len):
1462
row = row_list[i]
1463
value_row = value_list[i]
1464
for col in range(col_list_len):
1465
self.set_unsafe(row, col, self._coerce_element(value_row[col]))
1466
else:
1467
for i in range(row_list_len):
1468
row = row_list[i]
1469
value_row = value_list[i]
1470
for col in range(col_list_len):
1471
self.set_unsafe(row, col_list[col], self._coerce_element(value_row[col]))
1472
return
1473
1474
1475
1476
1477
cdef _coerce_element(self, x):
1478
"""
1479
Return coercion of x into the base ring of self.
1480
"""
1481
if PY_TYPE_CHECK(x, Element) and (<Element> x)._parent is self._base_ring:
1482
return x
1483
return self._base_ring(x)
1484
1485
###########################################################
1486
# Pickling
1487
###########################################################
1488
1489
def __reduce__(self):
1490
"""
1491
EXAMPLES::
1492
1493
sage: a = matrix(Integers(8),3,range(9))
1494
sage: a == loads(dumps(a))
1495
True
1496
"""
1497
data, version = self._pickle()
1498
return unpickle, (self.__class__, self._parent, self._is_immutable,
1499
self._cache, data, version)
1500
1501
def _pickle(self):
1502
"""
1503
Not yet implemented!
1504
1505
EXAMPLES::
1506
1507
sage: m=matrix(QQ,2,range(0,4))
1508
sage: m._pickle() # todo: not implemented
1509
"""
1510
raise NotImplementedError
1511
1512
def _test_reduce(self, **options):
1513
"""
1514
Checks that the pickling function works.
1515
1516
EXAMPLES::
1517
1518
sage: a=matrix([[1,2],[3,4]])
1519
sage: a._test_reduce()
1520
"""
1521
tester = self._tester(**options)
1522
a, b = self.__reduce__()
1523
tester.assertEqual(a(*b),self)
1524
1525
###########################################################
1526
# Base Change
1527
###########################################################
1528
def base_ring(self):
1529
"""
1530
Returns the base ring of the matrix.
1531
1532
EXAMPLES::
1533
1534
sage: m=matrix(QQ,2,[1,2,3,4])
1535
sage: m.base_ring()
1536
Rational Field
1537
"""
1538
return self._base_ring
1539
1540
def change_ring(self, ring):
1541
"""
1542
Return the matrix obtained by coercing the entries of this matrix
1543
into the given ring.
1544
1545
Always returns a copy (unless self is immutable, in which case
1546
returns self).
1547
1548
EXAMPLES::
1549
1550
sage: A = Matrix(QQ, 2, 2, [1/2, 1/3, 1/3, 1/4])
1551
sage: A.parent()
1552
Full MatrixSpace of 2 by 2 dense matrices over Rational Field
1553
sage: A.change_ring(GF(25,'a'))
1554
[3 2]
1555
[2 4]
1556
sage: A.change_ring(GF(25,'a')).parent()
1557
Full MatrixSpace of 2 by 2 dense matrices over Finite Field in a of size 5^2
1558
sage: A.change_ring(ZZ)
1559
Traceback (most recent call last):
1560
...
1561
TypeError: matrix has denominators so can't change to ZZ.
1562
1563
Changing rings preserves subdivisions::
1564
1565
sage: A.subdivide([1], []); A
1566
[1/2 1/3]
1567
[-------]
1568
[1/3 1/4]
1569
sage: A.change_ring(GF(25,'a'))
1570
[3 2]
1571
[---]
1572
[2 4]
1573
"""
1574
if not is_Ring(ring):
1575
raise TypeError("ring must be a ring")
1576
1577
if ring is self._base_ring:
1578
if self._is_immutable:
1579
return self
1580
return self.__copy__()
1581
1582
try:
1583
return self._change_ring(ring)
1584
except (AttributeError, NotImplementedError):
1585
M = sage.matrix.matrix_space.MatrixSpace(ring, self._nrows, self._ncols, sparse=self.is_sparse())
1586
mat = M(self.list(), coerce=True, copy=False)
1587
mat.subdivide(self.subdivisions())
1588
return mat
1589
1590
def _test_change_ring(self, **options):
1591
"""
1592
Checks that :meth:`change_ring` works.
1593
1594
EXAMPLES::
1595
1596
sage: a=matrix([[1,2],[3,4]])
1597
sage: a._test_change_ring()
1598
1599
"""
1600
tester = self._tester(**options)
1601
# Test to make sure the returned matrix is a copy
1602
tester.assert_(self.change_ring(self.base_ring()) is not self)
1603
1604
def _matrix_(self, R=None):
1605
"""
1606
Return ``self`` as a matrix over the ring ``R``. If ``R`` is ``None``,
1607
then return ``self``.
1608
1609
EXAMPLES::
1610
1611
sage: A = Matrix(ZZ[['t']], 2, 2, range(4))
1612
sage: A.parent()
1613
Full MatrixSpace of 2 by 2 dense matrices over Power Series Ring in t over Integer Ring
1614
sage: A._matrix_(QQ[['t']])
1615
[0 1]
1616
[2 3]
1617
sage: A._matrix_(QQ[['t']]).parent()
1618
Full MatrixSpace of 2 by 2 dense matrices over Power Series Ring in t over Rational Field
1619
1620
Check that :trac:`14314` is fixed::
1621
1622
sage: m = Matrix({(1,2):2})
1623
sage: matrix(m) == m
1624
True
1625
"""
1626
if R is None:
1627
return self
1628
return self.change_ring(R)
1629
1630
###########################################################
1631
# Representation -- string, latex, etc.
1632
###########################################################
1633
def __repr__(self):
1634
"""
1635
EXAMPLES::
1636
1637
sage: A = matrix([[1,2], [3,4], [5,6]])
1638
sage: A.__repr__()
1639
'[1 2]\n[3 4]\n[5 6]'
1640
sage: print A
1641
[1 2]
1642
[3 4]
1643
[5 6]
1644
1645
If the matrix is too big, don't print all of the elements::
1646
1647
sage: A = random_matrix(ZZ, 100)
1648
sage: A.__repr__()
1649
"100 x 100 dense matrix over Integer Ring (type 'print A.str()' to see all of the entries)"
1650
sage: print A
1651
100 x 100 dense matrix over Integer Ring (type 'print A.str()' to see all of the entries)
1652
1653
If there are several names for the same matrix, write it as "obj"::
1654
1655
sage: B = A; print B
1656
100 x 100 dense matrix over Integer Ring (type 'print obj.str()' to see all of the entries)
1657
1658
If the matrix doesn't have a name, don't print the extra string::
1659
1660
sage: A.transpose()
1661
100 x 100 dense matrix over Integer Ring
1662
sage: T = A.transpose(); T
1663
100 x 100 dense matrix over Integer Ring (type 'print T.str()' to see all of the entries)
1664
"""
1665
from sage.misc.sageinspect import sage_getvariablename
1666
if self._nrows < max_rows and self._ncols < max_cols:
1667
return self.str()
1668
if self.is_sparse():
1669
s = 'sparse'
1670
else:
1671
s = 'dense'
1672
rep = "%s x %s %s matrix over %s"%(self._nrows, self._ncols, s, self.base_ring())
1673
name = sage_getvariablename(self)
1674
if isinstance(name, list) and len(name) == 0:
1675
# don't print the name if the matrix doesn't have a name
1676
return rep
1677
if isinstance(name, list):
1678
name = [x for x in name if not x.startswith('_')]
1679
if len(name) == 1:
1680
name = name[0]
1681
# now name is either a string (if one choice) or a list (if many)
1682
if not isinstance(name, str):
1683
name = "obj"
1684
return rep + " (type 'print %s.str()' to see all of the entries)" % name
1685
1686
def str(self, rep_mapping=None, zero=None, plus_one=None, minus_one=None):
1687
r"""
1688
Return a nice string representation of the matrix.
1689
1690
INPUT:
1691
1692
- ``rep_mapping`` - a dictionary or callable used to override
1693
the usual representation of elements.
1694
1695
If ``rep_mapping`` is a dictionary then keys should be
1696
elements of the base ring and values the desired string
1697
representation. Values sent in via the other keyword
1698
arguments will override values in the dictionary.
1699
Use of a dictionary can potentially take a very long time
1700
due to the need to hash entries of the matrix. Matrices
1701
with entries from ``QQbar`` are one example.
1702
1703
If ``rep_mapping`` is callable then it will be called with
1704
elements of the matrix and must return a string. Simply
1705
call :func:`repr` on elements which should have the default
1706
representation.
1707
1708
- ``zero`` - string (default: ``None``); if not ``None`` use
1709
the value of ``zero`` as the representation of the zero
1710
element.
1711
1712
- ``plus_one`` - string (default: ``None``); if not ``None``
1713
use the value of ``plus_one`` as the representation of the
1714
one element.
1715
1716
- ``minus_one`` - string (default: ``None``); if not ``None``
1717
use the value of ``minus_one`` as the representation of the
1718
negative of the one element.
1719
1720
EXAMPLES::
1721
1722
sage: R = PolynomialRing(QQ,6,'z')
1723
sage: a = matrix(2,3, R.gens())
1724
sage: a.__repr__()
1725
'[z0 z1 z2]\n[z3 z4 z5]'
1726
1727
sage: M = matrix([[1,0],[2,-1]])
1728
sage: M.str()
1729
'[ 1 0]\n[ 2 -1]'
1730
sage: M.str(plus_one='+',minus_one='-',zero='.')
1731
'[+ .]\n[2 -]'
1732
sage: M.str({1:"not this one",2:"II"},minus_one="*",plus_one="I")
1733
'[ I 0]\n[II *]'
1734
1735
sage: def print_entry(x):
1736
... if x>0:
1737
... return '+'
1738
... elif x<0:
1739
... return '-'
1740
... else: return '.'
1741
...
1742
sage: M.str(print_entry)
1743
'[+ .]\n[+ -]'
1744
sage: M.str(repr)
1745
'[ 1 0]\n[ 2 -1]'
1746
1747
TESTS:
1748
1749
Prior to Trac #11544 this could take a full minute to run (2011). ::
1750
1751
sage: A = matrix(QQ, 4, 4, [1, 2, -2, 2, 1, 0, -1, -1, 0, -1, 1, 1, -1, 2, 1/2, 0])
1752
sage: e = A.eigenvalues()[3]
1753
sage: K = (A-e).kernel()
1754
sage: P = K.basis_matrix()
1755
sage: P.str()
1756
'[ 1.000000000000000? + 0.?e-17*I -2.116651487479748? + 0.0255565807096352?*I -0.2585224251020429? + 0.288602340904754?*I -0.4847545623533090? - 1.871890760086142?*I]'
1757
"""
1758
#x = self.fetch('repr') # too confusing!!
1759
#if not x is None: return x
1760
cdef Py_ssize_t nr, nc, r, c
1761
nr = self._nrows
1762
nc = self._ncols
1763
1764
if nr == 0 or nc == 0:
1765
return "[]"
1766
1767
row_divs, col_divs = self.subdivisions()
1768
1769
# Set the mapping based on keyword arguments
1770
if rep_mapping is None:
1771
rep_mapping = {}
1772
if isinstance(rep_mapping, dict):
1773
if zero is not None:
1774
rep_mapping[self.base_ring().zero()] = zero
1775
if plus_one is not None:
1776
rep_mapping[self.base_ring().one()] = plus_one
1777
if minus_one is not None:
1778
rep_mapping[-self.base_ring().one()] = minus_one
1779
1780
# compute column widths
1781
S = []
1782
for x in self.list():
1783
# Override the usual representations with those specified
1784
if callable(rep_mapping):
1785
rep = rep_mapping(x)
1786
# avoid hashing entries, especially algebraic numbers
1787
elif rep_mapping and rep_mapping.has_key(x):
1788
rep = rep_mapping.get(x)
1789
else:
1790
rep = repr(x)
1791
S.append(rep)
1792
1793
tmp = []
1794
for x in S:
1795
tmp.append(len(x))
1796
1797
width = max(tmp)
1798
rows = []
1799
m = 0
1800
1801
left_bracket = "["
1802
right_bracket = "]"
1803
while nc in col_divs:
1804
right_bracket = "|" + right_bracket
1805
col_divs.remove(nc)
1806
while 0 in col_divs:
1807
left_bracket += "|"
1808
col_divs.remove(0)
1809
line = '+'.join(['-'*((width+1)*(b-a)-1) for a,b in zip([0] + col_divs, col_divs + [nc])])
1810
hline = (left_bracket + line + right_bracket).replace('|', '+')
1811
1812
# compute rows
1813
for r from 0 <= r < nr:
1814
rows += [hline] * row_divs.count(r)
1815
s = ""
1816
for c from 0 <= c < nc:
1817
if c+1 in col_divs:
1818
sep = "|"*col_divs.count(c+1)
1819
elif c == nc - 1:
1820
sep=""
1821
else:
1822
sep=" "
1823
entry = S[r*nc+c]
1824
if c == 0:
1825
m = max(m, len(entry))
1826
entry = " "*(width-len(entry)) + entry
1827
s = s + entry + sep
1828
rows.append(left_bracket + s + right_bracket)
1829
1830
rows += [hline] * row_divs.count(nr)
1831
1832
s = "\n".join(rows)
1833
#self.cache('repr',s)
1834
return s
1835
1836
## def _latex_sparse(self, variable="x"):
1837
## r"""
1838
## Return a latex string that represents this matrix as a sparse
1839
## matrix. The rows are printed as sums $\sum a_i x_i$, where
1840
## $x$ is the variable.
1841
1842
## EXAMPLES:
1843
1844
## """
1845
## cdef Py_ssize_t nr, nc, i, j
1846
## nr = self._nrows
1847
## nc = self._ncols
1848
## s = "\\left(\\begin{align*}\n"
1849
## for i from 0 <= i < nr:
1850
## v = []
1851
## for j from 0 <= j < nc:
1852
## x = self.get_unsafe(i, j)
1853
## if x != 0:
1854
## v.append((j, x))
1855
## for j from 0 <= j < len(v):
1856
## s = s + "%s*%s_{%s}"%(v[j][1], variable, v[j][0])
1857
## if j == 0:
1858
## s = s + "& + "
1859
## elif j < len(v) - 1:
1860
## s = s + " + "
1861
## else:
1862
## s = s + "\\\\\n"
1863
## s = s + "\n\\end{align*}"
1864
## return s
1865
1866
def _latex_(self):
1867
r"""
1868
Return latex representation of this matrix. The matrix is
1869
enclosed in parentheses by default, but the delimiters can be
1870
changed using the command
1871
``latex.matrix_delimiters(...)``.
1872
1873
EXAMPLES::
1874
1875
sage: R = PolynomialRing(QQ,4,'z')
1876
sage: a = matrix(2,2, R.gens())
1877
sage: b = a*a
1878
sage: latex(b) # indirect doctest
1879
\left(\begin{array}{rr}
1880
z_{0}^{2} + z_{1} z_{2} & z_{0} z_{1} + z_{1} z_{3} \\
1881
z_{0} z_{2} + z_{2} z_{3} & z_{1} z_{2} + z_{3}^{2}
1882
\end{array}\right)
1883
1884
Latex representation for block matrices::
1885
1886
sage: B = matrix(3,4)
1887
sage: B.subdivide([2,2], [3])
1888
sage: latex(B)
1889
\left(\begin{array}{rrr|r}
1890
0 & 0 & 0 & 0 \\
1891
0 & 0 & 0 & 0 \\
1892
\hline\hline
1893
0 & 0 & 0 & 0
1894
\end{array}\right)
1895
"""
1896
latex = sage.misc.latex.latex
1897
matrix_delimiters = latex.matrix_delimiters()
1898
cdef Py_ssize_t nr, nc, r, c
1899
nr = self._nrows
1900
nc = self._ncols
1901
if nr == 0 or nc == 0:
1902
return matrix_delimiters[0] + matrix_delimiters[1]
1903
1904
S = self.list()
1905
rows = []
1906
1907
row_divs, col_divs = self.subdivisions()
1908
1909
# construct one large array, using \hline and vertical
1910
# bars | in the array descriptor to indicate subdivisions.
1911
for r from 0 <= r < nr:
1912
if r in row_divs:
1913
s = "\\hline"*row_divs.count(r) + "\n"
1914
else:
1915
s = ""
1916
for c from 0 <= c < nc:
1917
if c == nc-1:
1918
sep=""
1919
else:
1920
sep=" & "
1921
entry = latex(S[r*nc+c])
1922
s = s + entry + sep
1923
rows.append(s)
1924
1925
# Put brackets around in a single string
1926
tmp = []
1927
for row in rows:
1928
tmp.append(str(row))
1929
s = " \\\\\n".join(tmp)
1930
1931
tmp = ['r'*(b-a) for a,b in zip([0] + col_divs, col_divs + [nc])]
1932
format = '|'.join(tmp)
1933
1934
return "\\left" + matrix_delimiters[0] + "\\begin{array}{%s}\n"%format + s + "\n\\end{array}\\right" + matrix_delimiters[1]
1935
1936
1937
1938
###################################################
1939
## Basic Properties
1940
###################################################
1941
def ncols(self):
1942
"""
1943
Return the number of columns of this matrix.
1944
1945
EXAMPLES::
1946
1947
sage: M = MatrixSpace(QQ, 2, 3)
1948
sage: A = M([1,2,3, 4,5,6])
1949
sage: A
1950
[1 2 3]
1951
[4 5 6]
1952
sage: A.ncols()
1953
3
1954
sage: A.nrows()
1955
2
1956
1957
AUTHORS:
1958
1959
- Naqi Jaffery (2006-01-24): examples
1960
"""
1961
return self._ncols
1962
1963
def nrows(self):
1964
r"""
1965
Return the number of rows of this matrix.
1966
1967
EXAMPLES::
1968
1969
sage: M = MatrixSpace(QQ,6,7)
1970
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])
1971
sage: A
1972
[ 1 2 3 4 5 6 7]
1973
[ 22 3/4 34 11 7 5 3]
1974
[ 99 65 1/2 2/3 3/5 4/5 5/6]
1975
[ 9 8/9 9/8 7/6 6/7 76 4]
1976
[ 0 9 8 7 6 5 4]
1977
[ 123 99 91 28 6 1024 1]
1978
sage: A.ncols()
1979
7
1980
sage: A.nrows()
1981
6
1982
1983
AUTHORS:
1984
1985
- Naqi Jaffery (2006-01-24): examples
1986
"""
1987
return self._nrows
1988
1989
def dimensions(self):
1990
r"""
1991
Returns the dimensions of this matrix as the tuple (nrows, ncols).
1992
1993
EXAMPLES::
1994
1995
sage: M = matrix([[1,2,3],[4,5,6]])
1996
sage: N = M.transpose()
1997
sage: M.dimensions()
1998
(2, 3)
1999
sage: N.dimensions()
2000
(3, 2)
2001
2002
AUTHORS:
2003
2004
- Benjamin Lundell (2012-02-09): examples
2005
"""
2006
return (self._nrows,self._ncols)
2007
2008
2009
###################################################
2010
# Functions
2011
###################################################
2012
def act_on_polynomial(self, f):
2013
"""
2014
Returns the polynomial f(self\*x).
2015
2016
INPUT:
2017
2018
2019
- ``self`` - an nxn matrix
2020
2021
- ``f`` - a polynomial in n variables x=(x1,...,xn)
2022
2023
2024
OUTPUT: The polynomial f(self\*x).
2025
2026
EXAMPLES::
2027
2028
sage: R.<x,y> = QQ[]
2029
sage: x, y = R.gens()
2030
sage: f = x**2 - y**2
2031
sage: M = MatrixSpace(QQ, 2)
2032
sage: A = M([1,2,3,4])
2033
sage: A.act_on_polynomial(f)
2034
-8*x^2 - 20*x*y - 12*y^2
2035
"""
2036
cdef Py_ssize_t i, j, n
2037
2038
if self._nrows != self._ncols:
2039
raise ArithmeticError("self must be a square matrix")
2040
2041
F = f.base_ring()
2042
vars = f.parent().gens()
2043
n = len(self.rows())
2044
ans = []
2045
for i from 0 <= i < n:
2046
tmp = []
2047
for j from 0 <= j < n:
2048
tmp.append(self.get_unsafe(i,j)*vars[j])
2049
ans.append( sum(tmp) )
2050
return f(tuple(ans))
2051
2052
def __call__(self, *args, **kwargs):
2053
"""
2054
Calling a matrix returns the result of calling each component.
2055
2056
EXAMPLES::
2057
2058
sage: f(x,y) = x^2+y
2059
sage: m = matrix([[f,f*f],[f^3,f^4]]); m
2060
[ (x, y) |--> x^2 + y (x, y) |--> (x^2 + y)^2]
2061
[(x, y) |--> (x^2 + y)^3 (x, y) |--> (x^2 + y)^4]
2062
sage: m(1,2)
2063
[ 3 9]
2064
[27 81]
2065
sage: m(y=2,x=1)
2066
[ 3 9]
2067
[27 81]
2068
sage: m(2,1)
2069
[ 5 25]
2070
[125 625]
2071
"""
2072
from constructor import matrix
2073
return matrix(self.nrows(), self.ncols(), [e(*args, **kwargs) for e in self.list()])
2074
2075
###################################################
2076
# Arithmetic
2077
###################################################
2078
def commutator(self, other):
2079
"""
2080
Return the commutator self\*other - other\*self.
2081
2082
EXAMPLES::
2083
2084
sage: A = Matrix(ZZ, 2, 2, range(4))
2085
sage: B = Matrix(ZZ, 2, 2, [0, 1, 0, 0])
2086
sage: A.commutator(B)
2087
[-2 -3]
2088
[ 0 2]
2089
sage: A.commutator(B) == -B.commutator(A)
2090
True
2091
"""
2092
return self*other - other*self
2093
2094
def anticommutator(self, other):
2095
r"""
2096
Return the anticommutator ``self`` and ``other``.
2097
2098
The *anticommutator* of two `n \times n` matrices `A` and `B`
2099
is defined as `\{A, B\} := AB + BA` (sometimes this is written as
2100
`[A, B]_+`).
2101
2102
EXAMPLES::
2103
2104
sage: A = Matrix(ZZ, 2, 2, range(4))
2105
sage: B = Matrix(ZZ, 2, 2, [0, 1, 0, 0])
2106
sage: A.anticommutator(B)
2107
[2 3]
2108
[0 2]
2109
sage: A.anticommutator(B) == B.anticommutator(A)
2110
True
2111
sage: A.commutator(B) + B.anticommutator(A) == 2*A*B
2112
True
2113
"""
2114
return self*other + other*self
2115
2116
###################################################
2117
# Row and column operations
2118
# The _c versions do no bounds checking.
2119
# The with_ versions do not change the input matrix.
2120
# Some of the functions assume that input values
2121
# have parent that is self._base_ring.
2122
# AUTHORS:
2123
# -- Karl-Dieter Crisman (June 2008):
2124
# Improved examples and error messages for methods which could
2125
# involve multiplication outside base ring, including
2126
# with_ versions of these methods for this situation
2127
###################################################
2128
cdef check_row_bounds_and_mutability(self, Py_ssize_t r1, Py_ssize_t r2):
2129
if self._is_immutable:
2130
raise ValueError("matrix is immutable; please change a copy instead (i.e., use copy(M) to change a copy of M).")
2131
else:
2132
self._cache = None
2133
if r1<0 or r1 >= self._nrows or r2<0 or r2 >= self._nrows:
2134
raise IndexError("matrix row index out of range")
2135
2136
cdef check_column_bounds_and_mutability(self, Py_ssize_t c1, Py_ssize_t c2):
2137
if self._is_immutable:
2138
raise ValueError("matrix is immutable; please change a copy instead (i.e., use copy(M) to change a copy of M).")
2139
else:
2140
self._cache = None
2141
if c1<0 or c1 >= self._ncols or c2<0 or c2 >= self._ncols:
2142
raise IndexError("matrix column index out of range")
2143
2144
def swap_columns(self, Py_ssize_t c1, Py_ssize_t c2):
2145
"""
2146
Swap columns c1 and c2 of self.
2147
2148
EXAMPLES: We create a rational matrix::
2149
2150
sage: M = MatrixSpace(QQ,3,3)
2151
sage: A = M([1,9,-7,4/5,4,3,6,4,3])
2152
sage: A
2153
[ 1 9 -7]
2154
[4/5 4 3]
2155
[ 6 4 3]
2156
2157
Since the first column is numbered zero, this swaps the second and
2158
third columns::
2159
2160
sage: A.swap_columns(1,2); A
2161
[ 1 -7 9]
2162
[4/5 3 4]
2163
[ 6 3 4]
2164
"""
2165
self.check_column_bounds_and_mutability(c1, c2)
2166
if c1 != c2:
2167
self.swap_columns_c(c1, c2)
2168
2169
def with_swapped_columns(self, c1, c2):
2170
r"""
2171
Swap columns ``c1`` and ``c2`` of ``self`` and return a new matrix.
2172
2173
INPUT:
2174
2175
- ``c1``, ``c2`` - integers specifying columns of ``self`` to interchange
2176
2177
OUTPUT:
2178
2179
A new matrix, identical to ``self`` except that columns ``c1`` and ``c2``
2180
are swapped.
2181
2182
EXAMPLES:
2183
2184
Remember that columns are numbered starting from zero. ::
2185
2186
sage: A = matrix(QQ, 4, range(20))
2187
sage: A.with_swapped_columns(1, 2)
2188
[ 0 2 1 3 4]
2189
[ 5 7 6 8 9]
2190
[10 12 11 13 14]
2191
[15 17 16 18 19]
2192
2193
Trying to swap a column with itself will succeed, but still return
2194
a new matrix. ::
2195
2196
sage: A = matrix(QQ, 4, range(20))
2197
sage: B = A.with_swapped_columns(2, 2)
2198
sage: A == B
2199
True
2200
sage: A is B
2201
False
2202
2203
The column specifications are checked. ::
2204
2205
sage: A = matrix(4, range(20))
2206
sage: A.with_swapped_columns(-1, 2)
2207
Traceback (most recent call last):
2208
...
2209
IndexError: matrix column index out of range
2210
2211
sage: A.with_swapped_columns(2, 5)
2212
Traceback (most recent call last):
2213
...
2214
IndexError: matrix column index out of range
2215
"""
2216
cdef Matrix temp
2217
self.check_column_bounds_and_mutability(c1,c2)
2218
temp = self.__copy__()
2219
if c1 != c2:
2220
temp.swap_columns_c(c1,c2)
2221
return temp
2222
2223
cdef swap_columns_c(self, Py_ssize_t c1, Py_ssize_t c2):
2224
cdef Py_ssize_t r
2225
for r from 0 <= r < self._nrows:
2226
a = self.get_unsafe(r, c2)
2227
self.set_unsafe(r, c2, self.get_unsafe(r,c1))
2228
self.set_unsafe(r, c1, a)
2229
2230
def swap_rows(self, r1, r2):
2231
"""
2232
Swap rows r1 and r2 of self.
2233
2234
EXAMPLES: We create a rational matrix::
2235
2236
sage: M = MatrixSpace(QQ,3,3)
2237
sage: A = M([1,9,-7,4/5,4,3,6,4,3])
2238
sage: A
2239
[ 1 9 -7]
2240
[4/5 4 3]
2241
[ 6 4 3]
2242
2243
Since the first row is numbered zero, this swaps the first and
2244
third rows::
2245
2246
sage: A.swap_rows(0,2); A
2247
[ 6 4 3]
2248
[4/5 4 3]
2249
[ 1 9 -7]
2250
"""
2251
self.check_row_bounds_and_mutability(r1, r2)
2252
if r1 != r2:
2253
self.swap_rows_c(r1, r2)
2254
2255
def with_swapped_rows(self, r1, r2):
2256
r"""
2257
Swap rows ``r1`` and ``r2`` of ``self`` and return a new matrix.
2258
2259
INPUT:
2260
2261
- ``r1``, ``r2`` - integers specifying rows of ``self`` to interchange
2262
2263
OUTPUT:
2264
2265
A new matrix, identical to ``self`` except that rows ``r1`` and ``r2``
2266
are swapped.
2267
2268
EXAMPLES:
2269
2270
Remember that rows are numbered starting from zero. ::
2271
2272
sage: A = matrix(QQ, 4, range(20))
2273
sage: A.with_swapped_rows(1, 2)
2274
[ 0 1 2 3 4]
2275
[10 11 12 13 14]
2276
[ 5 6 7 8 9]
2277
[15 16 17 18 19]
2278
2279
Trying to swap a row with itself will succeed, but still return
2280
a new matrix. ::
2281
2282
sage: A = matrix(QQ, 4, range(20))
2283
sage: B = A.with_swapped_rows(2, 2)
2284
sage: A == B
2285
True
2286
sage: A is B
2287
False
2288
2289
The row specifications are checked. ::
2290
2291
sage: A = matrix(4, range(20))
2292
sage: A.with_swapped_rows(-1, 2)
2293
Traceback (most recent call last):
2294
...
2295
IndexError: matrix row index out of range
2296
2297
sage: A.with_swapped_rows(2, 5)
2298
Traceback (most recent call last):
2299
...
2300
IndexError: matrix row index out of range
2301
"""
2302
cdef Matrix temp
2303
self.check_row_bounds_and_mutability(r1,r2)
2304
temp = self.__copy__()
2305
if r1 != r2:
2306
temp.swap_rows_c(r1,r2)
2307
return temp
2308
2309
cdef swap_rows_c(self, Py_ssize_t r1, Py_ssize_t r2):
2310
cdef Py_ssize_t c
2311
for c from 0 <= c < self._ncols:
2312
a = self.get_unsafe(r2, c)
2313
self.set_unsafe(r2, c, self.get_unsafe(r1, c))
2314
self.set_unsafe(r1, c, a)
2315
2316
def add_multiple_of_row(self, Py_ssize_t i, Py_ssize_t j, s, Py_ssize_t start_col=0):
2317
"""
2318
Add s times row j to row i.
2319
2320
EXAMPLES: We add -3 times the first row to the second row of an
2321
integer matrix, remembering to start numbering rows at zero::
2322
2323
sage: a = matrix(ZZ,2,3,range(6)); a
2324
[0 1 2]
2325
[3 4 5]
2326
sage: a.add_multiple_of_row(1,0,-3)
2327
sage: a
2328
[ 0 1 2]
2329
[ 3 1 -1]
2330
2331
To add a rational multiple, we first need to change the base ring::
2332
2333
sage: a = a.change_ring(QQ)
2334
sage: a.add_multiple_of_row(1,0,1/3)
2335
sage: a
2336
[ 0 1 2]
2337
[ 3 4/3 -1/3]
2338
2339
If not, we get an error message::
2340
2341
sage: a.add_multiple_of_row(1,0,i)
2342
Traceback (most recent call last):
2343
...
2344
TypeError: Multiplying row by Symbolic Ring element cannot be done over Rational Field, use change_ring or with_added_multiple_of_row instead.
2345
"""
2346
self.check_row_bounds_and_mutability(i,j)
2347
try:
2348
s = self._coerce_element(s)
2349
self.add_multiple_of_row_c(i, j, s, start_col)
2350
except TypeError:
2351
raise TypeError('Multiplying row by %s element cannot be done over %s, use change_ring or with_added_multiple_of_row instead.' % (s.parent(), self.base_ring()))
2352
2353
cdef add_multiple_of_row_c(self, Py_ssize_t i, Py_ssize_t j, s, Py_ssize_t start_col):
2354
cdef Py_ssize_t c
2355
for c from start_col <= c < self._ncols:
2356
self.set_unsafe(i, c, self.get_unsafe(i, c) + s*self.get_unsafe(j, c))
2357
2358
def with_added_multiple_of_row(self, Py_ssize_t i, Py_ssize_t j, s, Py_ssize_t start_col=0):
2359
"""
2360
Add s times row j to row i, returning new matrix.
2361
2362
EXAMPLES: We add -3 times the first row to the second row of an
2363
integer matrix, remembering to start numbering rows at zero::
2364
2365
sage: a = matrix(ZZ,2,3,range(6)); a
2366
[0 1 2]
2367
[3 4 5]
2368
sage: b = a.with_added_multiple_of_row(1,0,-3); b
2369
[ 0 1 2]
2370
[ 3 1 -1]
2371
2372
The original matrix is unchanged::
2373
2374
sage: a
2375
[0 1 2]
2376
[3 4 5]
2377
2378
Adding a rational multiple is okay, and reassigning a variable is
2379
okay::
2380
2381
sage: a = a.with_added_multiple_of_row(0,1,1/3); a
2382
[ 1 7/3 11/3]
2383
[ 3 4 5]
2384
"""
2385
cdef Matrix temp
2386
self.check_row_bounds_and_mutability(i,j)
2387
try:
2388
s = self._coerce_element(s)
2389
temp = self.__copy__()
2390
temp.add_multiple_of_row_c(i, j, s, start_col)
2391
return temp
2392
# If scaling factor cannot be coerced, change the base ring to
2393
# one acceptable to both the original base ring and the scaling factor.
2394
except TypeError:
2395
temp = self.change_ring(Sequence([s,self.base_ring()(0)]).universe())
2396
s = temp._coerce_element(s)
2397
temp.add_multiple_of_row_c(i, j, s, start_col)
2398
return temp
2399
2400
def add_multiple_of_column(self, Py_ssize_t i, Py_ssize_t j, s, Py_ssize_t start_row=0):
2401
"""
2402
Add s times column j to column i.
2403
2404
EXAMPLES: We add -1 times the third column to the second column of
2405
an integer matrix, remembering to start numbering cols at zero::
2406
2407
sage: a = matrix(ZZ,2,3,range(6)); a
2408
[0 1 2]
2409
[3 4 5]
2410
sage: a.add_multiple_of_column(1,2,-1)
2411
sage: a
2412
[ 0 -1 2]
2413
[ 3 -1 5]
2414
2415
To add a rational multiple, we first need to change the base ring::
2416
2417
sage: a = a.change_ring(QQ)
2418
sage: a.add_multiple_of_column(1,0,1/3)
2419
sage: a
2420
[ 0 -1 2]
2421
[ 3 0 5]
2422
2423
If not, we get an error message::
2424
2425
sage: a.add_multiple_of_column(1,0,i)
2426
Traceback (most recent call last):
2427
...
2428
TypeError: Multiplying column by Symbolic Ring element cannot be done over Rational Field, use change_ring or with_added_multiple_of_column instead.
2429
"""
2430
self.check_column_bounds_and_mutability(i,j)
2431
try:
2432
s = self._coerce_element(s)
2433
self.add_multiple_of_column_c(i, j, s, start_row)
2434
except TypeError:
2435
raise TypeError('Multiplying column by %s element cannot be done over %s, use change_ring or with_added_multiple_of_column instead.' % (s.parent(), self.base_ring()))
2436
2437
cdef add_multiple_of_column_c(self, Py_ssize_t i, Py_ssize_t j, s, Py_ssize_t start_row):
2438
cdef Py_ssize_t r
2439
for r from start_row <= r < self._nrows:
2440
self.set_unsafe(r, i, self.get_unsafe(r, i) + s*self.get_unsafe(r, j))
2441
2442
def with_added_multiple_of_column(self, Py_ssize_t i, Py_ssize_t j, s, Py_ssize_t start_row=0):
2443
"""
2444
Add s times column j to column i, returning new matrix.
2445
2446
EXAMPLES: We add -1 times the third column to the second column of
2447
an integer matrix, remembering to start numbering cols at zero::
2448
2449
sage: a = matrix(ZZ,2,3,range(6)); a
2450
[0 1 2]
2451
[3 4 5]
2452
sage: b = a.with_added_multiple_of_column(1,2,-1); b
2453
[ 0 -1 2]
2454
[ 3 -1 5]
2455
2456
The original matrix is unchanged::
2457
2458
sage: a
2459
[0 1 2]
2460
[3 4 5]
2461
2462
Adding a rational multiple is okay, and reassigning a variable is
2463
okay::
2464
2465
sage: a = a.with_added_multiple_of_column(0,1,1/3); a
2466
[ 1/3 1 2]
2467
[13/3 4 5]
2468
"""
2469
cdef Matrix temp
2470
self.check_column_bounds_and_mutability(i,j)
2471
try:
2472
s = self._coerce_element(s)
2473
temp = self.__copy__()
2474
temp.add_multiple_of_column_c(i, j, s, start_row)
2475
return temp
2476
# If scaling factor cannot be coerced, change the base ring to
2477
# one acceptable to both the original base ring and the scaling factor.
2478
except TypeError:
2479
temp = self.change_ring(Sequence([s,self.base_ring()(0)]).universe())
2480
s = temp._coerce_element(s)
2481
temp.add_multiple_of_column_c(i, j, s, start_row)
2482
return temp
2483
2484
def rescale_row(self, Py_ssize_t i, s, Py_ssize_t start_col=0):
2485
"""
2486
Replace i-th row of self by s times i-th row of self.
2487
2488
INPUT:
2489
2490
2491
- ``i`` - ith row
2492
2493
- ``s`` - scalar
2494
2495
- ``start_col`` - only rescale entries at this column
2496
and to the right
2497
2498
2499
EXAMPLES: We rescale the second row of a matrix over the rational
2500
numbers::
2501
2502
sage: a = matrix(QQ,3,range(6)); a
2503
[0 1]
2504
[2 3]
2505
[4 5]
2506
sage: a.rescale_row(1,1/2); a
2507
[ 0 1]
2508
[ 1 3/2]
2509
[ 4 5]
2510
2511
We rescale the second row of a matrix over a polynomial ring::
2512
2513
sage: R.<x> = QQ[]
2514
sage: a = matrix(R,3,[1,x,x^2,x^3,x^4,x^5]);a
2515
[ 1 x]
2516
[x^2 x^3]
2517
[x^4 x^5]
2518
sage: a.rescale_row(1,1/2); a
2519
[ 1 x]
2520
[1/2*x^2 1/2*x^3]
2521
[ x^4 x^5]
2522
2523
We try and fail to rescale a matrix over the integers by a
2524
non-integer::
2525
2526
sage: a = matrix(ZZ,2,3,[0,1,2, 3,4,4]); a
2527
[0 1 2]
2528
[3 4 4]
2529
sage: a.rescale_row(1,1/2)
2530
Traceback (most recent call last):
2531
...
2532
TypeError: Rescaling row by Rational Field element cannot be done over Integer Ring, use change_ring or with_rescaled_row instead.
2533
2534
To rescale the matrix by 1/2, you must change the base ring to the
2535
rationals::
2536
2537
sage: a = a.change_ring(QQ); a
2538
[0 1 2]
2539
[3 4 4]
2540
sage: a.rescale_col(1,1/2); a
2541
[ 0 1/2 2]
2542
[ 3 2 4]
2543
"""
2544
self.check_row_bounds_and_mutability(i, i)
2545
try:
2546
s = self._coerce_element(s)
2547
self.rescale_row_c(i, s, start_col)
2548
except TypeError:
2549
raise TypeError('Rescaling row by %s element cannot be done over %s, use change_ring or with_rescaled_row instead.' % (s.parent(), self.base_ring()))
2550
2551
cdef rescale_row_c(self, Py_ssize_t i, s, Py_ssize_t start_col):
2552
cdef Py_ssize_t j
2553
for j from start_col <= j < self._ncols:
2554
self.set_unsafe(i, j, self.get_unsafe(i, j)*s)
2555
2556
def with_rescaled_row(self, Py_ssize_t i, s, Py_ssize_t start_col=0):
2557
"""
2558
Replaces i-th row of self by s times i-th row of self, returning
2559
new matrix.
2560
2561
EXAMPLES: We rescale the second row of a matrix over the integers::
2562
2563
sage: a = matrix(ZZ,3,2,range(6)); a
2564
[0 1]
2565
[2 3]
2566
[4 5]
2567
sage: b = a.with_rescaled_row(1,-2); b
2568
[ 0 1]
2569
[-4 -6]
2570
[ 4 5]
2571
2572
The original matrix is unchanged::
2573
2574
sage: a
2575
[0 1]
2576
[2 3]
2577
[4 5]
2578
2579
Adding a rational multiple is okay, and reassigning a variable is
2580
okay::
2581
2582
sage: a = a.with_rescaled_row(2,1/3); a
2583
[ 0 1]
2584
[ 2 3]
2585
[4/3 5/3]
2586
"""
2587
cdef Matrix temp
2588
self.check_row_bounds_and_mutability(i,i)
2589
try:
2590
s = self._coerce_element(s)
2591
temp = self.__copy__()
2592
temp.rescale_row_c(i, s, start_col)
2593
return temp
2594
# If scaling factor cannot be coerced, change the base ring to
2595
# one acceptable to both the original base ring and the scaling factor.
2596
except TypeError:
2597
temp = self.change_ring(Sequence([s,self.base_ring()(0)]).universe())
2598
s = temp._coerce_element(s)
2599
temp.rescale_row_c(i, s, start_col)
2600
return temp
2601
2602
def rescale_col(self, Py_ssize_t i, s, Py_ssize_t start_row=0):
2603
"""
2604
Replace i-th col of self by s times i-th col of self.
2605
2606
INPUT:
2607
2608
2609
- ``i`` - ith column
2610
2611
- ``s`` - scalar
2612
2613
- ``start_row`` - only rescale entries at this row
2614
and lower
2615
2616
2617
EXAMPLES: We rescale the last column of a matrix over the rational
2618
numbers::
2619
2620
sage: a = matrix(QQ,2,3,range(6)); a
2621
[0 1 2]
2622
[3 4 5]
2623
sage: a.rescale_col(2,1/2); a
2624
[ 0 1 1]
2625
[ 3 4 5/2]
2626
sage: R.<x> = QQ[]
2627
2628
We rescale the last column of a matrix over a polynomial ring::
2629
2630
sage: a = matrix(R,2,3,[1,x,x^2,x^3,x^4,x^5]); a
2631
[ 1 x x^2]
2632
[x^3 x^4 x^5]
2633
sage: a.rescale_col(2,1/2); a
2634
[ 1 x 1/2*x^2]
2635
[ x^3 x^4 1/2*x^5]
2636
2637
We try and fail to rescale a matrix over the integers by a
2638
non-integer::
2639
2640
sage: a = matrix(ZZ,2,3,[0,1,2, 3,4,4]); a
2641
[0 1 2]
2642
[3 4 4]
2643
sage: a.rescale_col(2,1/2)
2644
Traceback (most recent call last):
2645
...
2646
TypeError: Rescaling column by Rational Field element cannot be done over Integer Ring, use change_ring or with_rescaled_col instead.
2647
2648
To rescale the matrix by 1/2, you must change the base ring to the
2649
rationals::
2650
2651
sage: a = a.change_ring(QQ); a
2652
[0 1 2]
2653
[3 4 4]
2654
sage: a.rescale_col(2,1/2); a
2655
[0 1 1]
2656
[3 4 2]
2657
"""
2658
self.check_column_bounds_and_mutability(i, i)
2659
try:
2660
s = self._coerce_element(s)
2661
self.rescale_col_c(i, s, start_row)
2662
except TypeError:
2663
raise TypeError('Rescaling column by %s element cannot be done over %s, use change_ring or with_rescaled_col instead.' % (s.parent(), self.base_ring()))
2664
2665
cdef rescale_col_c(self, Py_ssize_t i, s, Py_ssize_t start_row):
2666
cdef Py_ssize_t j
2667
for j from start_row <= j < self._nrows:
2668
self.set_unsafe(j, i, self.get_unsafe(j, i)*s)
2669
2670
def with_rescaled_col(self, Py_ssize_t i, s, Py_ssize_t start_row=0):
2671
"""
2672
Replaces i-th col of self by s times i-th col of self, returning
2673
new matrix.
2674
2675
EXAMPLES: We rescale the last column of a matrix over the
2676
integers::
2677
2678
sage: a = matrix(ZZ,2,3,range(6)); a
2679
[0 1 2]
2680
[3 4 5]
2681
sage: b = a.with_rescaled_col(2,-2); b
2682
[ 0 1 -4]
2683
[ 3 4 -10]
2684
2685
The original matrix is unchanged::
2686
2687
sage: a
2688
[0 1 2]
2689
[3 4 5]
2690
2691
Adding a rational multiple is okay, and reassigning a variable is
2692
okay::
2693
2694
sage: a = a.with_rescaled_col(1,1/3); a
2695
[ 0 1/3 2]
2696
[ 3 4/3 5]
2697
"""
2698
cdef Matrix temp
2699
self.check_column_bounds_and_mutability(i,i)
2700
try:
2701
s = self._coerce_element(s)
2702
temp = self.__copy__()
2703
temp.rescale_col_c(i, s, start_row)
2704
return temp
2705
# If scaling factor cannot be coerced, change the base ring to
2706
# one acceptable to both the original base ring and the scaling factor.
2707
except TypeError:
2708
temp = self.change_ring(Sequence([s,self.base_ring()(0)]).universe())
2709
s = temp._coerce_element(s)
2710
temp.rescale_col_c(i, s, start_row)
2711
return temp
2712
2713
def set_row_to_multiple_of_row(self, Py_ssize_t i, Py_ssize_t j, s):
2714
"""
2715
Set row i equal to s times row j.
2716
2717
EXAMPLES: We change the second row to -3 times the first row::
2718
2719
sage: a = matrix(ZZ,2,3,range(6)); a
2720
[0 1 2]
2721
[3 4 5]
2722
sage: a.set_row_to_multiple_of_row(1,0,-3)
2723
sage: a
2724
[ 0 1 2]
2725
[ 0 -3 -6]
2726
2727
If we try to multiply a row by a rational number, we get an error
2728
message::
2729
2730
sage: a.set_row_to_multiple_of_row(1,0,1/2)
2731
Traceback (most recent call last):
2732
...
2733
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.
2734
"""
2735
self.check_row_bounds_and_mutability(i,j)
2736
cdef Py_ssize_t n
2737
try:
2738
s = self._coerce_element(s)
2739
for n from 0 <= n < self._ncols:
2740
self.set_unsafe(i, n, s * self.get_unsafe(j, n)) # self[i] = s*self[j]
2741
except TypeError:
2742
raise TypeError('Multiplying row by %s element cannot be done over %s, use change_ring or with_row_set_to_multiple_of_row instead.' % (s.parent(), self.base_ring()))
2743
2744
def with_row_set_to_multiple_of_row(self, Py_ssize_t i, Py_ssize_t j, s):
2745
"""
2746
Set row i equal to s times row j, returning a new matrix.
2747
2748
EXAMPLES: We change the second row to -3 times the first row::
2749
2750
sage: a = matrix(ZZ,2,3,range(6)); a
2751
[0 1 2]
2752
[3 4 5]
2753
sage: b = a.with_row_set_to_multiple_of_row(1,0,-3); b
2754
[ 0 1 2]
2755
[ 0 -3 -6]
2756
2757
Note that the original matrix is unchanged::
2758
2759
sage: a
2760
[0 1 2]
2761
[3 4 5]
2762
2763
Adding a rational multiple is okay, and reassigning a variable is
2764
okay::
2765
2766
sage: a = a.with_row_set_to_multiple_of_row(1,0,1/2); a
2767
[ 0 1 2]
2768
[ 0 1/2 1]
2769
"""
2770
self.check_row_bounds_and_mutability(i,j)
2771
cdef Matrix temp
2772
cdef Py_ssize_t n
2773
try:
2774
s = self._coerce_element(s)
2775
temp = self.__copy__()
2776
for n from 0 <= n < temp._ncols:
2777
temp.set_unsafe(i, n, s * temp.get_unsafe(j, n)) # temp[i] = s*temp[j]
2778
return temp
2779
# If scaling factor cannot be coerced, change the base ring to
2780
# one acceptable to both the original base ring and the scaling factor.
2781
except TypeError:
2782
temp = self.change_ring(Sequence([s,self.base_ring()(0)]).universe())
2783
s = temp._coerce_element(s)
2784
for n from 0 <= n < temp._ncols:
2785
temp.set_unsafe(i, n, s * temp.get_unsafe(j, n)) # temp[i] = s*temp[j]
2786
return temp
2787
2788
def set_col_to_multiple_of_col(self, Py_ssize_t i, Py_ssize_t j, s):
2789
"""
2790
Set column i equal to s times column j.
2791
2792
EXAMPLES: We change the second column to -3 times the first
2793
column.
2794
2795
::
2796
2797
sage: a = matrix(ZZ,2,3,range(6)); a
2798
[0 1 2]
2799
[3 4 5]
2800
sage: a.set_col_to_multiple_of_col(1,0,-3)
2801
sage: a
2802
[ 0 0 2]
2803
[ 3 -9 5]
2804
2805
If we try to multiply a column by a rational number, we get an
2806
error message::
2807
2808
sage: a.set_col_to_multiple_of_col(1,0,1/2)
2809
Traceback (most recent call last):
2810
...
2811
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.
2812
"""
2813
self.check_column_bounds_and_mutability(i,j)
2814
cdef Py_ssize_t n
2815
try:
2816
s = self._coerce_element(s)
2817
for n from 0 <= n < self._nrows:
2818
self.set_unsafe(n, i, s * self.get_unsafe(n, j))
2819
# If scaling factor cannot be coerced, change the base ring to
2820
# one acceptable to both the original base ring and the scaling factor.
2821
except TypeError:
2822
raise TypeError('Multiplying column by %s element cannot be done over %s, use change_ring or with_col_set_to_multiple_of_col instead.' % (s.parent(), self.base_ring()))
2823
2824
def with_col_set_to_multiple_of_col(self, Py_ssize_t i, Py_ssize_t j, s):
2825
"""
2826
Set column i equal to s times column j, returning a new matrix.
2827
2828
EXAMPLES: We change the second column to -3 times the first
2829
column.
2830
2831
::
2832
2833
sage: a = matrix(ZZ,2,3,range(6)); a
2834
[0 1 2]
2835
[3 4 5]
2836
sage: b = a.with_col_set_to_multiple_of_col(1,0,-3); b
2837
[ 0 0 2]
2838
[ 3 -9 5]
2839
2840
Note that the original matrix is unchanged::
2841
2842
sage: a
2843
[0 1 2]
2844
[3 4 5]
2845
2846
Adding a rational multiple is okay, and reassigning a variable is
2847
okay::
2848
2849
sage: a = a.with_col_set_to_multiple_of_col(1,0,1/2); a
2850
[ 0 0 2]
2851
[ 3 3/2 5]
2852
"""
2853
self.check_column_bounds_and_mutability(i,j)
2854
cdef Py_ssize_t n
2855
cdef Matrix temp
2856
try:
2857
s = self._coerce_element(s)
2858
temp = self.__copy__()
2859
for n from 0 <= n < temp._nrows:
2860
temp.set_unsafe(n, i, s * temp.get_unsafe(n, j))
2861
return temp
2862
# If scaling factor cannot be coerced, change the base ring to
2863
# one acceptable to both the original base ring and the scaling factor.
2864
except TypeError:
2865
temp = self.change_ring(Sequence([s,self.base_ring()(0)]).universe())
2866
s = temp._coerce_element(s)
2867
for n from 0 <= n < temp._nrows:
2868
temp.set_unsafe(n, i, s * temp.get_unsafe(n, j))
2869
return temp
2870
2871
def _set_row_to_negative_of_row_of_A_using_subset_of_columns(self, Py_ssize_t i, Matrix A,
2872
Py_ssize_t r, cols,
2873
cols_index=None):
2874
"""
2875
Set row i of self to -(row r of A), but where we only take the
2876
given column positions in that row of A. We do not zero out the
2877
other entries of self's row i either.
2878
2879
INPUT:
2880
2881
2882
- ``i`` - integer, index into the rows of self
2883
2884
- ``A`` - a matrix
2885
2886
- ``r`` - integer, index into rows of A
2887
2888
- ``cols`` - a *sorted* list of integers.
2889
2890
- ``(cols_index`` - ignored)
2891
2892
2893
EXAMPLES::
2894
2895
sage: a = matrix(QQ,2,3,range(6)); a
2896
[0 1 2]
2897
[3 4 5]
2898
sage: a._set_row_to_negative_of_row_of_A_using_subset_of_columns(0,a,1,[1,2])
2899
sage: a
2900
[-4 -5 2]
2901
[ 3 4 5]
2902
"""
2903
self.check_row_bounds_and_mutability(i,i)
2904
if r < 0 or r >= A.nrows():
2905
raise IndexError("invalid row")
2906
# this function exists just because it is useful for modular symbols presentations.
2907
cdef Py_ssize_t l
2908
l = 0
2909
for k in cols:
2910
self.set_unsafe(i,l,-A.get_unsafe(r,k)) #self[i,l] = -A[r,k]
2911
l += 1
2912
2913
###################################################
2914
# Methods needed for quiver and cluster mutations
2915
# - mutate
2916
# - _travel_column
2917
# - is_symmetrizable
2918
# - is_skew_symmetrizable
2919
# - _check_symmetrizability
2920
#
2921
# AUTHORS:
2922
# -- Christian Stump (Jun 2011)
2923
###################################################
2924
2925
def mutate(self, Py_ssize_t k ):
2926
"""
2927
Mutates ``self`` at row and column index ``k``.
2928
2929
.. warning:: Only makes sense if ``self`` is skew-symmetrizable.
2930
2931
INPUT:
2932
2933
- ``k`` -- integer at which row/column ``self`` is mutated.
2934
2935
EXAMPLES:
2936
2937
Mutation of the B-matrix of the quiver of type `A_3`::
2938
2939
sage: M = matrix(ZZ,3,[0,1,0,-1,0,-1,0,1,0]); M
2940
[ 0 1 0]
2941
[-1 0 -1]
2942
[ 0 1 0]
2943
2944
sage: M.mutate(0); M
2945
[ 0 -1 0]
2946
[ 1 0 -1]
2947
[ 0 1 0]
2948
2949
sage: M.mutate(1); M
2950
[ 0 1 -1]
2951
[-1 0 1]
2952
[ 1 -1 0]
2953
2954
sage: M = matrix(ZZ,6,[0,1,0,-1,0,-1,0,1,0,1,0,0,0,1,0,0,0,1]); M
2955
[ 0 1 0]
2956
[-1 0 -1]
2957
[ 0 1 0]
2958
[ 1 0 0]
2959
[ 0 1 0]
2960
[ 0 0 1]
2961
2962
sage: M.mutate(0); M
2963
[ 0 -1 0]
2964
[ 1 0 -1]
2965
[ 0 1 0]
2966
[-1 1 0]
2967
[ 0 1 0]
2968
[ 0 0 1]
2969
2970
REFERENCES:
2971
2972
- [FZ2001] S. Fomin, A. Zelevinsky. Cluster Algebras 1: Foundations, arXiv:math/0104151 (2001).
2973
"""
2974
cdef Py_ssize_t i,j,_
2975
cdef list pairs, k0_pairs, k1_pairs
2976
2977
if k < 0 or k >= self._nrows or k >= self._ncols:
2978
raise IndexError("The mutation index is invalid")
2979
2980
pairs = self.nonzero_positions()
2981
k0_pairs = [ pair for pair in pairs if pair[0] == k ]
2982
k1_pairs = [ pair for pair in pairs if pair[1] == k ]
2983
for _,j in k0_pairs:
2984
self[k,j] = -self.get_unsafe(k,j)
2985
for i,_ in k1_pairs:
2986
self[i,k] = -self.get_unsafe(i,k)
2987
2988
for i,_ in k1_pairs:
2989
ik = self.get_unsafe(i,k)
2990
ineg = True if ik < 0 else False
2991
for _,j in k0_pairs:
2992
kj = self.get_unsafe(k,j)
2993
jneg = True if kj < 0 else False
2994
if ineg == jneg == True:
2995
self[i,j] = self.get_unsafe(i,j) + self.get_unsafe(i,k)*self.get_unsafe(k,j)
2996
elif ineg == jneg == False:
2997
self[i,j] = self.get_unsafe(i,j) - self.get_unsafe(i,k)*self.get_unsafe(k,j)
2998
2999
def _travel_column( self, dict d, int k, int sign, positive ):
3000
r"""
3001
Helper function for testing symmetrizability. Tests dependencies within entries in ``self`` and entries in the dictionary ``d``.
3002
3003
.. warning:: the dictionary ``d`` gets new values for keys in L.
3004
3005
INPUT:
3006
3007
- ``d`` -- dictionary modelling partial entries of a diagonal matrix.
3008
3009
- ``k`` -- integer for which row and column of self should be tested with the dictionary d.
3010
3011
- ``sign`` -- `\pm 1`, depending on symmetric or skew-symmetric is tested.
3012
3013
- ``positive`` -- if True, only positive entries for the values of the dictionary are allowed.
3014
3015
OUTPUT:
3016
3017
- ``L`` -- list of new keys in d
3018
3019
EXAMPLES::
3020
3021
sage: M = matrix(ZZ,3,[0,1,0,-1,0,-1,0,1,0]); M
3022
[ 0 1 0]
3023
[-1 0 -1]
3024
[ 0 1 0]
3025
3026
sage: M._travel_column({0:1},0,-1,True)
3027
[1]
3028
"""
3029
cdef list L = []
3030
cdef int i
3031
3032
for i from 0 <= i < self._ncols:
3033
if i not in d:
3034
self_ik = self.get_unsafe(i,k)
3035
self_ki = self.get_unsafe(k,i)
3036
if bool(self_ik) != bool(self_ki):
3037
return False
3038
if self_ik != 0:
3039
L.append(i)
3040
d[i] = sign * d[k] * self_ki / self_ik
3041
if positive and not d[i] > 0:
3042
return False
3043
for j in d:
3044
if d[i] * self.get_unsafe(i,j) != sign * d[j] * self.get_unsafe(j,i):
3045
return False
3046
return L
3047
3048
def _check_symmetrizability(self, return_diag=False, skew=False, positive=True):
3049
r"""
3050
This function takes a square matrix over an *ordered integral domain* and checks if it is (skew-)symmetrizable.
3051
A matrix `B` is (skew-)symmetrizable iff there exists an invertible diagonal matrix `D` such that `DB` is (skew-)symmetric.
3052
3053
INPUT:
3054
3055
- ``return_diag`` -- bool(default:False) if True and ``self`` is (skew)-symmetrizable the diagonal entries of the matrix `D` are returned.
3056
- ``skew`` -- bool(default:False) if True, (skew-)symmetrizability is checked.
3057
- ``positive`` -- bool(default:True) if True, the condition that `D` has positive entries is added.
3058
3059
OUTPUT:
3060
3061
- True -- if ``self`` is (skew-)symmetrizable and ``return_diag`` is False
3062
- the diagonal entries of the matrix `D` such that `DB` is (skew-)symmetric -- iff ``self`` is (skew-)symmetrizable and ``return_diag`` is True
3063
- False -- iff ``self`` is not (skew-)symmetrizable
3064
3065
EXAMPLES::
3066
3067
sage: matrix([[0,6],[3,0]])._check_symmetrizability(positive=False)
3068
True
3069
sage: matrix([[0,6],[3,0]])._check_symmetrizability(positive=True)
3070
True
3071
sage: matrix([[0,6],[3,0]])._check_symmetrizability(skew=True, positive=False)
3072
True
3073
sage: matrix([[0,6],[3,0]])._check_symmetrizability(skew=True, positive=True)
3074
False
3075
3076
REFERENCES:
3077
3078
- [FZ2001] S. Fomin, A. Zelevinsky. Cluster Algebras 1: Foundations, arXiv:math/0104151 (2001).
3079
"""
3080
cdef dict d = {}
3081
cdef list queue = range( self._ncols )
3082
cdef int l, sign, i, j
3083
3084
if skew:
3085
# testing the diagonal entries to be zero
3086
zero = self.parent().base_ring().zero()
3087
for i from 0 <= i < self._nrows:
3088
if not self.get_unsafe(i,i) == zero:
3089
return False
3090
sign = -1
3091
else:
3092
sign = 1
3093
3094
while queue:
3095
i = queue.pop(0)
3096
d[i] = 1
3097
L = self._travel_column( d, i, sign, positive )
3098
if L is False:
3099
return False
3100
while L:
3101
l = L.pop(0)
3102
queue.remove( l )
3103
L_prime = self._travel_column( d, l, sign, positive )
3104
if L_prime is False:
3105
return False
3106
else:
3107
L.extend( L_prime )
3108
if return_diag:
3109
return [ d[i] for i in xrange(self._nrows) ]
3110
else:
3111
return True
3112
3113
###################################################
3114
# Matrix-vector multiply
3115
###################################################
3116
def linear_combination_of_rows(self, v):
3117
r"""
3118
Return the linear combination of the rows of ``self`` given by the
3119
coefficients in the list ``v``.
3120
3121
INPUT:
3122
3123
- ``v`` - a list of scalars. The length can be less than
3124
the number of rows of ``self`` but not greater.
3125
3126
OUTPUT:
3127
3128
The vector (or free module element) that is a linear
3129
combination of the rows of ``self``. If the list of
3130
scalars has fewer entries than the number of rows,
3131
additional zeros are appended to the list until it
3132
has as many entries as the number of rows.
3133
3134
EXAMPLES::
3135
3136
sage: a = matrix(ZZ,2,3,range(6)); a
3137
[0 1 2]
3138
[3 4 5]
3139
sage: a.linear_combination_of_rows([1,2])
3140
(6, 9, 12)
3141
3142
sage: a.linear_combination_of_rows([0,0])
3143
(0, 0, 0)
3144
3145
sage: a.linear_combination_of_rows([1/2,2/3])
3146
(2, 19/6, 13/3)
3147
3148
The list ``v`` can be anything that is iterable. Perhaps most
3149
naturally, a vector may be used. ::
3150
3151
sage: v = vector(ZZ, [1,2])
3152
sage: a.linear_combination_of_rows(v)
3153
(6, 9, 12)
3154
3155
We check that a matrix with no rows behaves properly. ::
3156
3157
sage: matrix(QQ,0,2).linear_combination_of_rows([])
3158
(0, 0)
3159
3160
The object returned is a vector, or a free module element. ::
3161
3162
sage: B = matrix(ZZ, 4, 3, range(12))
3163
sage: w = B.linear_combination_of_rows([-1,2,-3,4])
3164
sage: w
3165
(24, 26, 28)
3166
sage: w.parent()
3167
Ambient free module of rank 3 over the principal ideal domain Integer Ring
3168
sage: x = B.linear_combination_of_rows([1/2,1/3,1/4,1/5])
3169
sage: x
3170
(43/10, 67/12, 103/15)
3171
sage: x.parent()
3172
Vector space of dimension 3 over Rational Field
3173
3174
The length of v can be less than the number of rows, but not
3175
greater. ::
3176
3177
sage: A = matrix(QQ,3,4,range(12))
3178
sage: A.linear_combination_of_rows([2,3])
3179
(12, 17, 22, 27)
3180
sage: A.linear_combination_of_rows([1,2,3,4])
3181
Traceback (most recent call last):
3182
...
3183
ValueError: length of v must be at most the number of rows of self
3184
"""
3185
if len(v) > self._nrows:
3186
raise ValueError("length of v must be at most the number of rows of self")
3187
if self._nrows == 0:
3188
return self.parent().row_space().zero_vector()
3189
from constructor import matrix
3190
v = matrix(list(v)+[0]*(self._nrows-len(v)))
3191
return (v * self)[0]
3192
3193
def linear_combination_of_columns(self, v):
3194
r"""
3195
Return the linear combination of the columns of ``self`` given by the
3196
coefficients in the list ``v``.
3197
3198
INPUT:
3199
3200
- ``v`` - a list of scalars. The length can be less than
3201
the number of columns of ``self`` but not greater.
3202
3203
OUTPUT:
3204
3205
The vector (or free module element) that is a linear
3206
combination of the columns of ``self``. If the list of
3207
scalars has fewer entries than the number of columns,
3208
additional zeros are appended to the list until it
3209
has as many entries as the number of columns.
3210
3211
EXAMPLES::
3212
3213
sage: a = matrix(ZZ,2,3,range(6)); a
3214
[0 1 2]
3215
[3 4 5]
3216
sage: a.linear_combination_of_columns([1,1,1])
3217
(3, 12)
3218
3219
sage: a.linear_combination_of_columns([0,0,0])
3220
(0, 0)
3221
3222
sage: a.linear_combination_of_columns([1/2,2/3,3/4])
3223
(13/6, 95/12)
3224
3225
The list ``v`` can be anything that is iterable. Perhaps most
3226
naturally, a vector may be used. ::
3227
3228
sage: v = vector(ZZ, [1,2,3])
3229
sage: a.linear_combination_of_columns(v)
3230
(8, 26)
3231
3232
We check that a matrix with no columns behaves properly. ::
3233
3234
sage: matrix(QQ,2,0).linear_combination_of_columns([])
3235
(0, 0)
3236
3237
The object returned is a vector, or a free module element. ::
3238
3239
sage: B = matrix(ZZ, 4, 3, range(12))
3240
sage: w = B.linear_combination_of_columns([-1,2,-3])
3241
sage: w
3242
(-4, -10, -16, -22)
3243
sage: w.parent()
3244
Ambient free module of rank 4 over the principal ideal domain Integer Ring
3245
sage: x = B.linear_combination_of_columns([1/2,1/3,1/4])
3246
sage: x
3247
(5/6, 49/12, 22/3, 127/12)
3248
sage: x.parent()
3249
Vector space of dimension 4 over Rational Field
3250
3251
The length of v can be less than the number of columns, but not
3252
greater. ::
3253
3254
sage: A = matrix(QQ,3,5, range(15))
3255
sage: A.linear_combination_of_columns([1,-2,3,-4])
3256
(-8, -18, -28)
3257
sage: A.linear_combination_of_columns([1,2,3,4,5,6])
3258
Traceback (most recent call last):
3259
...
3260
ValueError: length of v must be at most the number of columns of self
3261
"""
3262
if len(v) > self._ncols:
3263
raise ValueError("length of v must be at most the number of columns of self")
3264
if self._ncols == 0:
3265
return self.parent().column_space().zero_vector()
3266
from constructor import matrix
3267
v = matrix(self._ncols, 1, list(v)+[0]*(self._ncols-len(v)))
3268
return (self * v).column(0)
3269
3270
###################################################
3271
# Predicates
3272
###################################################
3273
3274
def is_symmetric(self):
3275
"""
3276
Returns True if this is a symmetric matrix.
3277
3278
EXAMPLES::
3279
3280
sage: m=Matrix(QQ,2,range(0,4))
3281
sage: m.is_symmetric()
3282
False
3283
3284
sage: m=Matrix(QQ,2,(1,1,1,1,1,1))
3285
sage: m.is_symmetric()
3286
False
3287
3288
sage: m=Matrix(QQ,1,(2,))
3289
sage: m.is_symmetric()
3290
True
3291
3292
"""
3293
if self._ncols != self._nrows: return False
3294
# could be bigger than an int on a 64-bit platform, this
3295
# is the type used for indexing.
3296
cdef Py_ssize_t i,j
3297
3298
for i from 0 <= i < self._nrows:
3299
for j from 0 <= j < i:
3300
if self.get_unsafe(i,j) != self.get_unsafe(j,i):
3301
return False
3302
return True
3303
3304
def is_hermitian(self):
3305
r"""
3306
Returns ``True`` if the matrix is equal to its conjugate-transpose.
3307
3308
OUTPUT:
3309
3310
``True`` if the matrix is square and equal to the transpose
3311
with every entry conjugated, and ``False`` otherwise.
3312
3313
Note that if conjugation has no effect on elements of the base
3314
ring (such as for integers), then the :meth:`is_symmetric`
3315
method is equivalent and faster.
3316
3317
This routine is for matrices over exact rings and so may not
3318
work properly for matrices over ``RR`` or ``CC``. For matrices with
3319
approximate entries, the rings of double-precision floating-point
3320
numbers, ``RDF`` and ``CDF``, are a better choice since the
3321
:meth:`sage.matrix.matrix_double_dense.Matrix_double_dense.is_hermitian`
3322
method has a tolerance parameter. This provides control over
3323
allowing for minor discrepancies between entries when checking
3324
equality.
3325
3326
The result is cached.
3327
3328
EXAMPLES::
3329
3330
sage: A = matrix(QQbar, [[ 1 + I, 1 - 6*I, -1 - I],
3331
... [-3 - I, -4*I, -2],
3332
... [-1 + I, -2 - 8*I, 2 + I]])
3333
sage: A.is_hermitian()
3334
False
3335
sage: B = A*A.conjugate_transpose()
3336
sage: B.is_hermitian()
3337
True
3338
3339
Sage has several fields besides the entire complex numbers
3340
where conjugation is non-trivial. ::
3341
3342
sage: F.<b> = QuadraticField(-7)
3343
sage: C = matrix(F, [[-2*b - 3, 7*b - 6, -b + 3],
3344
... [-2*b - 3, -3*b + 2, -2*b],
3345
... [ b + 1, 0, -2]])
3346
sage: C.is_hermitian()
3347
False
3348
sage: C = C*C.conjugate_transpose()
3349
sage: C.is_hermitian()
3350
True
3351
3352
A matrix that is nearly Hermitian, but for a non-real
3353
diagonal entry. ::
3354
3355
sage: A = matrix(QQbar, [[ 2, 2-I, 1+4*I],
3356
... [ 2+I, 3+I, 2-6*I],
3357
... [1-4*I, 2+6*I, 5]])
3358
sage: A.is_hermitian()
3359
False
3360
sage: A[1,1] = 132
3361
sage: A.is_hermitian()
3362
True
3363
3364
Rectangular matrices are never Hermitian. ::
3365
3366
sage: A = matrix(QQbar, 3, 4)
3367
sage: A.is_hermitian()
3368
False
3369
3370
A square, empty matrix is trivially Hermitian. ::
3371
3372
sage: A = matrix(QQ, 0, 0)
3373
sage: A.is_hermitian()
3374
True
3375
"""
3376
key = 'hermitian'
3377
h = self.fetch(key)
3378
if not h is None:
3379
return h
3380
if not self.is_square():
3381
self.cache(key, False)
3382
return False
3383
if self._nrows == 0:
3384
self.cache(key, True)
3385
return True
3386
3387
cdef Py_ssize_t i,j
3388
hermitian = True
3389
for i in range(self._nrows):
3390
for j in range(i+1):
3391
if self.get_unsafe(i,j) != self.get_unsafe(j,i).conjugate():
3392
hermitian = False
3393
break
3394
if not hermitian:
3395
break
3396
self.cache(key, hermitian)
3397
return hermitian
3398
3399
def is_skew_symmetric(self):
3400
"""
3401
Return ``True`` if ``self`` is a skew-symmetric matrix.
3402
3403
Here, "skew-symmetric matrix" means a square matrix `A`
3404
satisfying `A^T = -A`. It does not require that the
3405
diagonal entries of `A` are `0` (although this
3406
automatically follows from `A^T = -A` when `2` is
3407
invertible in the ground ring over which the matrix is
3408
considered). Skew-symmetric matrices `A` whose diagonal
3409
entries are `0` are said to be "alternating", and this
3410
property is checked by the :meth:`is_alternating`
3411
method.
3412
3413
EXAMPLES::
3414
3415
sage: m = matrix(QQ, [[0,2], [-2,0]])
3416
sage: m.is_skew_symmetric()
3417
True
3418
sage: m = matrix(QQ, [[1,2], [2,1]])
3419
sage: m.is_skew_symmetric()
3420
False
3421
3422
Skew-symmetric is not the same as alternating when
3423
`2` is a zero-divisor in the ground ring::
3424
3425
sage: n = matrix(Zmod(4), [[0, 1], [-1, 2]])
3426
sage: n.is_skew_symmetric()
3427
True
3428
3429
but yet the diagonal cannot be completely
3430
arbitrary in this case::
3431
3432
sage: n = matrix(Zmod(4), [[0, 1], [-1, 3]])
3433
sage: n.is_skew_symmetric()
3434
False
3435
"""
3436
if self._ncols != self._nrows: return False
3437
# could be bigger than an int on a 64-bit platform, this
3438
# is the type used for indexing.
3439
cdef Py_ssize_t i,j
3440
3441
for i from 0 <= i < self._nrows:
3442
for j from 0 <= j <= i:
3443
if self.get_unsafe(i,j) != -self.get_unsafe(j,i):
3444
return False
3445
return True
3446
3447
def is_alternating(self):
3448
"""
3449
Return ``True`` if ``self`` is an alternating matrix.
3450
3451
Here, "alternating matrix" means a square matrix `A`
3452
satisfying `A^T = -A` and such that the diagonal entries
3453
of `0`. Notice that the condition that the diagonal
3454
entries be `0` is not redundant for matrices over
3455
arbitrary ground rings (but it is redundant when `2` is
3456
invertible in the ground ring). A square matrix `A` only
3457
required to satisfy `A^T = -A` is said to be
3458
"skew-symmetric", and this property is checked by the
3459
:meth:`is_skew_symmetric` method.
3460
3461
EXAMPLES::
3462
3463
sage: m = matrix(QQ, [[0,2], [-2,0]])
3464
sage: m.is_alternating()
3465
True
3466
sage: m = matrix(QQ, [[1,2], [2,1]])
3467
sage: m.is_alternating()
3468
False
3469
3470
In contrast to the property of being skew-symmetric, the
3471
property of being alternating does not tolerate nonzero
3472
entries on the diagonal even if they are their own
3473
negatives::
3474
3475
sage: n = matrix(Zmod(4), [[0, 1], [-1, 2]])
3476
sage: n.is_alternating()
3477
False
3478
"""
3479
if self._ncols != self._nrows: return False
3480
# could be bigger than an int on a 64-bit platform, this
3481
# is the type used for indexing.
3482
cdef Py_ssize_t i,j
3483
3484
for i from 0 <= i < self._nrows:
3485
for j from 0 <= j < i:
3486
if self.get_unsafe(i,j) != -self.get_unsafe(j,i):
3487
return False
3488
if self.get_unsafe(i,i) != 0:
3489
return False
3490
return True
3491
3492
def is_symmetrizable(self, return_diag=False, positive=True):
3493
r"""
3494
This function takes a square matrix over an *ordered integral domain* and checks if it is symmetrizable.
3495
A matrix `B` is symmetrizable iff there exists an invertible diagonal matrix `D` such that `DB` is symmetric.
3496
3497
.. warning:: Expects ``self`` to be a matrix over an *ordered integral domain*.
3498
3499
INPUT:
3500
3501
- ``return_diag`` -- bool(default:False) if True and ``self`` is symmetrizable the diagonal entries of the matrix `D` are returned.
3502
- ``positive`` -- bool(default:True) if True, the condition that `D` has positive entries is added.
3503
3504
OUTPUT:
3505
3506
- True -- if ``self`` is symmetrizable and ``return_diag`` is False
3507
- the diagonal entries of a matrix `D` such that `DB` is symmetric -- iff ``self`` is symmetrizable and ``return_diag`` is True
3508
- False -- iff ``self`` is not symmetrizable
3509
3510
EXAMPLES::
3511
3512
sage: matrix([[0,6],[3,0]]).is_symmetrizable(positive=False)
3513
True
3514
3515
sage: matrix([[0,6],[3,0]]).is_symmetrizable(positive=True)
3516
True
3517
3518
sage: matrix([[0,6],[0,0]]).is_symmetrizable(return_diag=True)
3519
False
3520
3521
sage: matrix([2]).is_symmetrizable(positive=True)
3522
True
3523
3524
sage: matrix([[1,2],[3,4]]).is_symmetrizable(return_diag=true)
3525
[1, 2/3]
3526
3527
REFERENCES:
3528
3529
- [FZ2001] S. Fomin, A. Zelevinsky. Cluster Algebras 1: Foundations, arXiv:math/0104151 (2001).
3530
"""
3531
if self._ncols != self._nrows:
3532
raise ValueError, "The matrix is not a square matrix"
3533
return self._check_symmetrizability(return_diag=return_diag, skew=False, positive=positive)
3534
3535
def is_skew_symmetrizable(self, return_diag=False, positive=True):
3536
r"""
3537
This function takes a square matrix over an *ordered integral domain* and checks if it is skew-symmetrizable.
3538
A matrix `B` is skew-symmetrizable iff there exists an invertible diagonal matrix `D` such that `DB` is skew-symmetric.
3539
3540
.. warning:: Expects ``self`` to be a matrix over an *ordered integral domain*.
3541
3542
INPUT:
3543
3544
- ``return_diag`` -- bool(default:False) if True and ``self`` is skew-symmetrizable the diagonal entries of the matrix `D` are returned.
3545
- ``positive`` -- bool(default:True) if True, the condition that `D` has positive entries is added.
3546
3547
OUTPUT:
3548
3549
- True -- if ``self`` is skew-symmetrizable and ``return_diag`` is False
3550
- the diagonal entries of a matrix `D` such that `DB` is skew-symmetric -- iff ``self`` is skew-symmetrizable and ``return_diag`` is True
3551
- False -- iff ``self`` is not skew-symmetrizable
3552
3553
EXAMPLES::
3554
3555
sage: matrix([[0,6],[3,0]]).is_skew_symmetrizable(positive=False)
3556
True
3557
sage: matrix([[0,6],[3,0]]).is_skew_symmetrizable(positive=True)
3558
False
3559
3560
sage: M = matrix(4,[0,1,0,0,-1,0,-1,0,0,2,0,1,0,0,-1,0]); M
3561
[ 0 1 0 0]
3562
[-1 0 -1 0]
3563
[ 0 2 0 1]
3564
[ 0 0 -1 0]
3565
3566
sage: M.is_skew_symmetrizable(return_diag=True)
3567
[1, 1, 1/2, 1/2]
3568
3569
sage: M2 = diagonal_matrix([1,1,1/2,1/2])*M; M2
3570
[ 0 1 0 0]
3571
[ -1 0 -1 0]
3572
[ 0 1 0 1/2]
3573
[ 0 0 -1/2 0]
3574
3575
sage: M2.is_skew_symmetric()
3576
True
3577
3578
REFERENCES:
3579
3580
- [FZ2001] S. Fomin, A. Zelevinsky. Cluster Algebras 1: Foundations, arXiv:math/0104151 (2001).
3581
"""
3582
if self._ncols != self._nrows:
3583
raise ValueError, "The matrix is not a square matrix"
3584
return self._check_symmetrizability(return_diag=return_diag, skew=True, positive=positive)
3585
3586
def is_dense(self):
3587
"""
3588
Returns True if this is a dense matrix.
3589
3590
In Sage, being dense is a property of the underlying
3591
representation, not the number of nonzero entries.
3592
3593
EXAMPLES::
3594
3595
sage: matrix(QQ,2,2,range(4)).is_dense()
3596
True
3597
sage: matrix(QQ,2,2,range(4),sparse=True).is_dense()
3598
False
3599
"""
3600
return self.is_dense_c()
3601
3602
def is_sparse(self):
3603
"""
3604
Return True if this is a sparse matrix.
3605
3606
In Sage, being sparse is a property of the underlying
3607
representation, not the number of nonzero entries.
3608
3609
EXAMPLES::
3610
3611
sage: matrix(QQ,2,2,range(4)).is_sparse()
3612
False
3613
sage: matrix(QQ,2,2,range(4),sparse=True).is_sparse()
3614
True
3615
"""
3616
return self.is_sparse_c()
3617
3618
def is_square(self):
3619
"""
3620
Return True precisely if this matrix is square, i.e., has the same
3621
number of rows and columns.
3622
3623
EXAMPLES::
3624
3625
sage: matrix(QQ,2,2,range(4)).is_square()
3626
True
3627
sage: matrix(QQ,2,3,range(6)).is_square()
3628
False
3629
"""
3630
return self._nrows == self._ncols
3631
3632
def is_invertible(self):
3633
r"""
3634
Return True if this matrix is invertible.
3635
3636
EXAMPLES: The following matrix is invertible over
3637
`\QQ` but not over `\ZZ`.
3638
3639
::
3640
3641
sage: A = MatrixSpace(ZZ, 2)(range(4))
3642
sage: A.is_invertible()
3643
False
3644
sage: A.matrix_over_field().is_invertible()
3645
True
3646
3647
The inverse function is a constructor for matrices over the
3648
fraction field, so it can work even if A is not invertible.
3649
3650
::
3651
3652
sage: ~A # inverse of A
3653
[-3/2 1/2]
3654
[ 1 0]
3655
3656
The next matrix is invertible over `\ZZ`.
3657
3658
::
3659
3660
sage: A = MatrixSpace(IntegerRing(),2)([1,10,0,-1])
3661
sage: A.is_invertible()
3662
True
3663
sage: ~A # compute the inverse
3664
[ 1 10]
3665
[ 0 -1]
3666
3667
The following nontrivial matrix is invertible over
3668
`\ZZ[x]`.
3669
3670
::
3671
3672
sage: R.<x> = PolynomialRing(IntegerRing())
3673
sage: A = MatrixSpace(R,2)([1,x,0,-1])
3674
sage: A.is_invertible()
3675
True
3676
sage: ~A
3677
[ 1 x]
3678
[ 0 -1]
3679
"""
3680
return self.is_square() and self.determinant().is_unit()
3681
3682
def is_singular(self):
3683
r"""
3684
Returns ``True`` if ``self`` is singular.
3685
3686
OUTPUT:
3687
3688
A square matrix is singular if it has a zero
3689
determinant and this method will return ``True``
3690
in exactly this case. When the entries of the
3691
matrix come from a field, this is equivalent
3692
to having a nontrivial kernel, or lacking an
3693
inverse, or having linearly dependent rows,
3694
or having linearly dependent columns.
3695
3696
For square matrices over a field the methods
3697
:meth:`is_invertible` and :meth:`is_singular`
3698
are logical opposites. However, it is an error
3699
to apply :meth:`is_singular` to a matrix that
3700
is not square, while :meth:`is_invertible` will
3701
always return ``False`` for a matrix that is not
3702
square.
3703
3704
EXAMPLES:
3705
3706
A singular matrix over the field ``QQ``. ::
3707
3708
sage: A = matrix(QQ, 4, [-1,2,-3,6,0,-1,-1,0,-1,1,-5,7,-1,6,5,2])
3709
sage: A.is_singular()
3710
True
3711
sage: A.right_kernel().dimension()
3712
1
3713
3714
A matrix that is not singular, i.e. nonsingular, over a field. ::
3715
3716
sage: B = matrix(QQ, 4, [1,-3,-1,-5,2,-5,-2,-7,-2,5,3,4,-1,4,2,6])
3717
sage: B.is_singular()
3718
False
3719
sage: B.left_kernel().dimension()
3720
0
3721
3722
For "rectangular" matrices, invertibility is always
3723
``False``, but asking about singularity will give an error. ::
3724
3725
sage: C = matrix(QQ, 5, range(30))
3726
sage: C.is_invertible()
3727
False
3728
sage: C.is_singular()
3729
Traceback (most recent call last):
3730
...
3731
ValueError: self must be a square matrix
3732
3733
When the base ring is not a field, then a matrix
3734
may be both not invertible and not singular. ::
3735
3736
sage: D = matrix(ZZ, 4, [2,0,-4,8,2,1,-2,7,2,5,7,0,0,1,4,-6])
3737
sage: D.is_invertible()
3738
False
3739
sage: D.is_singular()
3740
False
3741
sage: d = D.determinant(); d
3742
2
3743
sage: d.is_unit()
3744
False
3745
"""
3746
if self.ncols() == self.nrows():
3747
return self.rank() != self.nrows()
3748
else:
3749
raise ValueError("self must be a square matrix")
3750
3751
###################################################
3752
# Invariants of a matrix
3753
###################################################
3754
3755
def pivots(self):
3756
"""
3757
Return the pivot column positions of this matrix.
3758
3759
OUTPUT: a tuple of Python integers: the position of the
3760
first nonzero entry in each row of the echelon form.
3761
3762
This returns a tuple so it is immutable; see #10752.
3763
3764
EXAMPLES::
3765
3766
sage: A = matrix(QQ, 2, 2, range(4))
3767
sage: A.pivots()
3768
(0, 1)
3769
"""
3770
x = self.fetch('pivots')
3771
if not x is None: return tuple(x)
3772
self.echelon_form()
3773
x = self.fetch('pivots')
3774
if x is None:
3775
print self
3776
print self.nrows()
3777
print self.dict()
3778
raise RuntimeError("BUG: matrix pivots should have been set but weren't, matrix parent = '%s'"%self.parent())
3779
return tuple(x)
3780
3781
def rank(self):
3782
"""
3783
3784
TESTS:
3785
3786
We should be able to compute the rank of a matrix whose
3787
entries are polynomials over a finite field (trac #5014)::
3788
3789
sage: P.<x> = PolynomialRing(GF(17))
3790
sage: m = matrix(P, [ [ 6*x^2 + 8*x + 12, 10*x^2 + 4*x + 11],
3791
... [8*x^2 + 12*x + 15, 8*x^2 + 9*x + 16] ])
3792
sage: m.rank()
3793
2
3794
3795
"""
3796
x = self.fetch('rank')
3797
if not x is None: return x
3798
if self._nrows == 0 or self._ncols == 0:
3799
return 0
3800
r = len(self.pivots())
3801
self.cache('rank', r)
3802
return r
3803
3804
cdef _set_pivots(self, X):
3805
self.cache('pivots', X)
3806
3807
def nonpivots(self):
3808
"""
3809
Return the list of i such that the i-th column of self is NOT a
3810
pivot column of the reduced row echelon form of self.
3811
3812
OUTPUT: sorted tuple of (Python) integers
3813
3814
EXAMPLES::
3815
3816
sage: a = matrix(QQ,3,3,range(9)); a
3817
[0 1 2]
3818
[3 4 5]
3819
[6 7 8]
3820
sage: a.echelon_form()
3821
[ 1 0 -1]
3822
[ 0 1 2]
3823
[ 0 0 0]
3824
sage: a.nonpivots()
3825
(2,)
3826
"""
3827
x = self.fetch('nonpivots')
3828
if not x is None: return tuple(x)
3829
3830
X = set(self.pivots())
3831
np = []
3832
for j in xrange(self.ncols()):
3833
if not (j in X):
3834
np.append(j)
3835
np = tuple(np)
3836
self.cache('nonpivots',np)
3837
return np
3838
3839
def nonzero_positions(self, copy=True, column_order=False):
3840
"""
3841
Returns the sorted list of pairs (i,j) such that self[i,j] != 0.
3842
3843
INPUT:
3844
3845
3846
- ``copy`` - (default: True) It is safe to change the
3847
resulting list (unless you give the option copy=False).
3848
3849
- ``column_order`` - (default: False) If true,
3850
returns the list of pairs (i,j) such that self[i,j] != 0, but
3851
sorted by columns, i.e., column j=0 entries occur first, then
3852
column j=1 entries, etc.
3853
3854
3855
EXAMPLES::
3856
3857
sage: a = matrix(QQ, 2,3, [1,2,0,2,0,0]); a
3858
[1 2 0]
3859
[2 0 0]
3860
sage: a.nonzero_positions()
3861
[(0, 0), (0, 1), (1, 0)]
3862
sage: a.nonzero_positions(copy=False)
3863
[(0, 0), (0, 1), (1, 0)]
3864
sage: a.nonzero_positions(column_order=True)
3865
[(0, 0), (1, 0), (0, 1)]
3866
sage: a = matrix(QQ, 2,3, [1,2,0,2,0,0], sparse=True); a
3867
[1 2 0]
3868
[2 0 0]
3869
sage: a.nonzero_positions()
3870
[(0, 0), (0, 1), (1, 0)]
3871
sage: a.nonzero_positions(copy=False)
3872
[(0, 0), (0, 1), (1, 0)]
3873
sage: a.nonzero_positions(column_order=True)
3874
[(0, 0), (1, 0), (0, 1)]
3875
"""
3876
if column_order:
3877
return self._nonzero_positions_by_column(copy)
3878
else:
3879
return self._nonzero_positions_by_row(copy)
3880
3881
def _nonzero_positions_by_row(self, copy=True):
3882
"""
3883
Returns the list of pairs (i,j) such that self[i,j] != 0.
3884
3885
It is safe to change the resulting list (unless you give the option copy=False).
3886
3887
EXAMPLE::
3888
3889
sage: M = Matrix(CC, [[1,0],[0,1]], sparse=True)
3890
sage: M._nonzero_positions_by_row()
3891
[(0, 0), (1, 1)]
3892
3893
"""
3894
x = self.fetch('nonzero_positions')
3895
if not x is None:
3896
if copy:
3897
return list(x)
3898
return x
3899
cdef Py_ssize_t i, j
3900
z = self._base_ring(0)
3901
nzp = []
3902
for i from 0 <= i < self._nrows:
3903
for j from 0 <= j < self._ncols:
3904
if self.get_unsafe(i,j) != z:
3905
nzp.append((i,j))
3906
self.cache('nonzero_positions', nzp)
3907
if copy:
3908
return list(nzp)
3909
return nzp
3910
3911
def _nonzero_positions_by_column(self, copy=True):
3912
"""
3913
Returns the list of pairs (i,j) such that self[i,j] != 0, but
3914
sorted by columns, i.e., column j=0 entries occur first, then
3915
column j=1 entries, etc.
3916
3917
It is safe to change the resulting list (unless you give the option
3918
copy=False).
3919
3920
EXAMPLES::
3921
3922
sage: m=matrix(QQ,2,[1,0,1,1,1,0])
3923
sage: m._nonzero_positions_by_column()
3924
[(0, 0), (1, 0), (1, 1), (0, 2)]
3925
3926
"""
3927
x = self.fetch('nonzero_positions_by_column')
3928
if not x is None:
3929
if copy:
3930
return list(x)
3931
return x
3932
cdef Py_ssize_t i, j
3933
z = self._base_ring(0)
3934
nzp = []
3935
for j from 0 <= j < self._ncols:
3936
for i from 0 <= i < self._nrows:
3937
if self.get_unsafe(i,j) != z:
3938
nzp.append((i,j))
3939
self.cache('nonzero_positions_by_column', nzp)
3940
if copy:
3941
return list(nzp)
3942
return nzp
3943
3944
def nonzero_positions_in_column(self, Py_ssize_t i):
3945
"""
3946
Return a sorted list of the integers j such that self[j,i] is
3947
nonzero, i.e., such that the j-th position of the i-th column is
3948
nonzero.
3949
3950
INPUT:
3951
3952
3953
- ``i`` - an integer
3954
3955
3956
OUTPUT: list
3957
3958
EXAMPLES::
3959
3960
sage: a = matrix(QQ, 3,2, [1,2,0,2,0,0]); a
3961
[1 2]
3962
[0 2]
3963
[0 0]
3964
sage: a.nonzero_positions_in_column(0)
3965
[0]
3966
sage: a.nonzero_positions_in_column(1)
3967
[0, 1]
3968
3969
You'll get an IndexError, if you select an invalid column::
3970
3971
sage: a.nonzero_positions_in_column(2)
3972
Traceback (most recent call last):
3973
...
3974
IndexError: matrix column index out of range
3975
"""
3976
cdef Py_ssize_t j
3977
z = self._base_ring(0)
3978
tmp = []
3979
3980
if i<0 or i >= self._ncols:
3981
raise IndexError("matrix column index out of range")
3982
for j from 0 <= j < self._nrows:
3983
if self.get_unsafe(j,i) != z:
3984
tmp.append(j)
3985
return tmp
3986
3987
def nonzero_positions_in_row(self, Py_ssize_t i):
3988
"""
3989
Return the integers j such that self[i,j] is nonzero, i.e., such
3990
that the j-th position of the i-th row is nonzero.
3991
3992
INPUT:
3993
3994
3995
- ``i`` - an integer
3996
3997
3998
OUTPUT: list
3999
4000
EXAMPLES::
4001
4002
sage: a = matrix(QQ, 3,2, [1,2,0,2,0,0]); a
4003
[1 2]
4004
[0 2]
4005
[0 0]
4006
sage: a.nonzero_positions_in_row(0)
4007
[0, 1]
4008
sage: a.nonzero_positions_in_row(1)
4009
[1]
4010
sage: a.nonzero_positions_in_row(2)
4011
[]
4012
"""
4013
cdef Py_ssize_t j
4014
4015
if i<0 or i >= self._nrows:
4016
raise IndexError("matrix row index out of range")
4017
4018
z = self._base_ring(0)
4019
tmp = []
4020
4021
for j from 0 <= j < self._ncols:
4022
if self.get_unsafe(i,j) != z:
4023
tmp.append(j)
4024
return tmp
4025
4026
def multiplicative_order(self):
4027
"""
4028
Return the multiplicative order of this matrix, which must
4029
therefore be invertible.
4030
4031
EXAMPLES::
4032
4033
sage: A = matrix(GF(59),3,[10,56,39,53,56,33,58,24,55])
4034
sage: A.multiplicative_order()
4035
580
4036
sage: (A^580).is_one()
4037
True
4038
4039
::
4040
4041
sage: B = matrix(GF(10007^3,'b'),0)
4042
sage: B.multiplicative_order()
4043
1
4044
4045
::
4046
4047
sage: C = matrix(GF(2^10,'c'),2,3,[1]*6)
4048
sage: C.multiplicative_order()
4049
Traceback (most recent call last):
4050
...
4051
ArithmeticError: self must be invertible ...
4052
4053
::
4054
4055
sage: D = matrix(IntegerModRing(6),3,[5,5,3,0,2,5,5,4,0])
4056
sage: D.multiplicative_order()
4057
Traceback (most recent call last):
4058
...
4059
NotImplementedError: ... only ... over finite fields
4060
4061
::
4062
4063
sage: E = MatrixSpace(GF(11^2,'e'),5).random_element()
4064
sage: (E^E.multiplicative_order()).is_one()
4065
True
4066
4067
REFERENCES:
4068
4069
- Frank Celler and C. R. Leedham-Green, "Calculating the Order of an Invertible Matrix", 1997
4070
4071
"""
4072
if not self.is_invertible():
4073
raise ArithmeticError("self must be invertible to have a multiplicative order")
4074
K = self.base_ring()
4075
if not (K.is_field() and K.is_finite()):
4076
raise NotImplementedError("multiplicative order is only implemented for matrices over finite fields")
4077
from sage.rings.integer import Integer
4078
from sage.groups.generic import order_from_multiple
4079
P = self.minimal_polynomial()
4080
if P.degree()==0: #the empty square matrix
4081
return 1
4082
R = P.parent()
4083
P = P.factor()
4084
q = K.cardinality()
4085
p = K.characteristic()
4086
a = 0
4087
res = Integer(1)
4088
for f,m in P:
4089
a = max(a,m)
4090
S = R.quotient(f,'y')
4091
res = res._lcm(order_from_multiple(S.gen(),q**f.degree()-1,operation='*'))
4092
ppart = p**Integer(a).exact_log(p)
4093
if ppart<a: ppart*=p
4094
return res*ppart
4095
4096
###################################################
4097
# Arithmetic
4098
###################################################
4099
cdef Vector _vector_times_matrix_(self, Vector v):
4100
"""
4101
Returns the vector times matrix product.
4102
4103
INPUT:
4104
4105
4106
- ``v`` - a free module element.
4107
4108
4109
OUTPUT: The vector times matrix product v\*A.
4110
4111
EXAMPLES::
4112
4113
sage: B = matrix(QQ,2, [1,2,3,4])
4114
sage: V = VectorSpace(QQ, 2)
4115
sage: v = V([-1,5])
4116
sage: v*B
4117
(14, 18)
4118
sage: -1*B.row(0) + 5*B.row(1)
4119
(14, 18)
4120
sage: B*v # computes B*v, where v is interpreted as a column vector.
4121
(9, 17)
4122
sage: -1*B.column(0) + 5*B.column(1)
4123
(9, 17)
4124
4125
We mix dense and sparse over different rings::
4126
4127
sage: v = FreeModule(ZZ, 3, sparse=True)([1, 2, 3])
4128
sage: m = matrix(QQ, 3, 4, range(12))
4129
sage: v * m
4130
(32, 38, 44, 50)
4131
sage: v = FreeModule(ZZ, 3, sparse=False)([1, 2, 3])
4132
sage: m = matrix(QQ, 3, 4, range(12), sparse=True)
4133
sage: v * m
4134
(32, 38, 44, 50)
4135
sage: (v * m).parent() is m.row(0).parent()
4136
True
4137
"""
4138
M = sage.modules.free_module.FreeModule(self._base_ring, self.ncols(), sparse=self.is_sparse())
4139
if self.nrows() != v.degree():
4140
raise ArithmeticError("number of rows of matrix must equal degree of vector")
4141
s = M(0)
4142
zero = self.base_ring()(0)
4143
cdef Py_ssize_t i
4144
for i from 0 <= i < self._nrows:
4145
if v[i] != zero:
4146
s += v[i]*self.row(i, from_list=True)
4147
return s
4148
4149
cdef Vector _matrix_times_vector_(self, Vector v):
4150
"""
4151
EXAMPLES::
4152
4153
sage: v = FreeModule(ZZ, 3, sparse=True)([1, 2, 3])
4154
sage: m = matrix(QQ, 4, 3, range(12))
4155
sage: m * v
4156
(8, 26, 44, 62)
4157
sage: v = FreeModule(ZZ, 3, sparse=False)([1, 2, 3])
4158
sage: m = matrix(QQ, 4, 3, range(12), sparse=True)
4159
sage: m * v
4160
(8, 26, 44, 62)
4161
sage: (m * v).parent() is m.column(0).parent()
4162
True
4163
"""
4164
M = sage.modules.free_module.FreeModule(self._base_ring, self.nrows(), sparse=self.is_sparse())
4165
if not PY_TYPE_CHECK(v, sage.modules.free_module_element.FreeModuleElement):
4166
v = M(v)
4167
if self.ncols() != v.degree():
4168
raise ArithmeticError("number of columns of matrix must equal degree of vector")
4169
s = M(0)
4170
for i in xrange(self.ncols()):
4171
if v[i] != 0:
4172
s = s + self.column(i, from_list=True)*v[i]
4173
return s
4174
4175
def iterates(self, v, n, rows=True):
4176
r"""
4177
Let `A` be this matrix and `v` be a free module
4178
element. If rows is True, return a matrix whose rows are the
4179
entries of the following vectors:
4180
4181
.. math::
4182
4183
v, v A, v A^2, \ldots, v A^{n-1}.
4184
4185
If rows is False, return a matrix whose columns are the entries of
4186
the following vectors:
4187
4188
.. math::
4189
4190
v, Av, A^2 v, \ldots, A^{n-1} v.
4191
4192
INPUT:
4193
4194
- ``v`` - free module element
4195
4196
- ``n`` - nonnegative integer
4197
4198
EXAMPLES::
4199
4200
sage: A = matrix(ZZ,2, [1,1,3,5]); A
4201
[1 1]
4202
[3 5]
4203
sage: v = vector([1,0])
4204
sage: A.iterates(v,0)
4205
[]
4206
sage: A.iterates(v,5)
4207
[ 1 0]
4208
[ 1 1]
4209
[ 4 6]
4210
[ 22 34]
4211
[124 192]
4212
4213
Another example::
4214
4215
sage: a = matrix(ZZ,3,range(9)); a
4216
[0 1 2]
4217
[3 4 5]
4218
[6 7 8]
4219
sage: v = vector([1,0,0])
4220
sage: a.iterates(v,4)
4221
[ 1 0 0]
4222
[ 0 1 2]
4223
[ 15 18 21]
4224
[180 234 288]
4225
sage: a.iterates(v,4,rows=False)
4226
[ 1 0 15 180]
4227
[ 0 3 42 558]
4228
[ 0 6 69 936]
4229
"""
4230
n = int(n)
4231
if n >= 2 and self.nrows() != self.ncols():
4232
raise ArithmeticError("matrix must be square if n >= 2.")
4233
if n == 0:
4234
return self.matrix_space(n, self.ncols())(0)
4235
m = self.nrows()
4236
M = sage.modules.free_module.FreeModule(self._base_ring, m, sparse=self.is_sparse())
4237
v = M(v)
4238
X = [v]
4239
4240
if rows:
4241
for _ in range(n-1):
4242
X.append(X[len(X)-1]*self)
4243
MS = self.matrix_space(n, m)
4244
return MS(X)
4245
else:
4246
for _ in range(n-1):
4247
X.append(self*X[len(X)-1])
4248
MS = self.matrix_space(n, m)
4249
return MS(X).transpose()
4250
4251
cpdef ModuleElement _add_(self, ModuleElement right):
4252
"""
4253
Add two matrices with the same parent.
4254
4255
EXAMPLES::
4256
4257
sage: R.<x,y> = FreeAlgebra(QQ,2)
4258
sage: a = matrix(2,2, [1,2,x*y,y*x])
4259
sage: b = matrix(2,2, [1,2,y*x,y*x])
4260
sage: a+b # indirect doctest
4261
[ 2 4]
4262
[x*y + y*x 2*y*x]
4263
4264
"""
4265
cdef Py_ssize_t i, j
4266
cdef Matrix A
4267
A = self.new_matrix()
4268
for i from 0 <= i < self._nrows:
4269
for j from 0 <= j < self._ncols:
4270
A.set_unsafe(i,j, self.get_unsafe(i,j) + (<Matrix>right).get_unsafe(i,j))
4271
return A
4272
4273
cpdef ModuleElement _sub_(self, ModuleElement right):
4274
"""
4275
Subtract two matrices with the same parent.
4276
4277
EXAMPLES::
4278
4279
sage: R.<x,y> = FreeAlgebra(QQ,2)
4280
sage: a = matrix(2,2, [1,2,x*y,y*x])
4281
sage: b = matrix(2,2, [1,2,y*x,y*x])
4282
sage: a-b # indirect doctest
4283
[ 0 0]
4284
[x*y - y*x 0]
4285
4286
"""
4287
cdef Py_ssize_t i, j
4288
cdef Matrix A
4289
A = self.new_matrix()
4290
for i from 0 <= i < self._nrows:
4291
for j from 0 <= j < self._ncols:
4292
A.set_unsafe(i,j, self.get_unsafe(i,j) - (<Matrix>right).get_unsafe(i,j))
4293
return A
4294
4295
4296
def __mod__(self, p):
4297
r"""
4298
Return matrix mod `p`, returning again a matrix over the
4299
same base ring.
4300
4301
.. note::
4302
4303
Use ``A.Mod(p)`` to obtain a matrix over the residue class
4304
ring modulo `p`.
4305
4306
EXAMPLES::
4307
4308
sage: M = Matrix(ZZ, 2, 2, [5, 9, 13, 15])
4309
sage: M % 7
4310
[5 2]
4311
[6 1]
4312
sage: parent(M % 7)
4313
Full MatrixSpace of 2 by 2 dense matrices over Integer Ring
4314
"""
4315
cdef Py_ssize_t i
4316
v = self.list()
4317
for i from 0 <= i < len(v):
4318
v[i] = v[i] % p
4319
return self.new_matrix(entries = v, copy=False, coerce=True)
4320
4321
def mod(self, p):
4322
"""
4323
Return matrix mod `p`, over the reduced ring.
4324
4325
EXAMPLES::
4326
4327
sage: M = matrix(ZZ, 2, 2, [5, 9, 13, 15])
4328
sage: M.mod(7)
4329
[5 2]
4330
[6 1]
4331
sage: parent(M.mod(7))
4332
Full MatrixSpace of 2 by 2 dense matrices over Ring of integers modulo 7
4333
"""
4334
return self.change_ring(self._base_ring.quotient_ring(p))
4335
4336
4337
cpdef ModuleElement _rmul_(self, RingElement left):
4338
"""
4339
EXAMPLES::
4340
4341
sage: a = matrix(QQ['x'],2,range(6))
4342
sage: (3/4) * a
4343
[ 0 3/4 3/2]
4344
[ 9/4 3 15/4]
4345
4346
sage: R.<x,y> = QQ[]
4347
sage: a = matrix(R,2,3,[1,x,y,-x*y,x+y,x-y]); a
4348
[ 1 x y]
4349
[ -x*y x + y x - y]
4350
sage: (x*y) * a
4351
[ x*y x^2*y x*y^2]
4352
[ -x^2*y^2 x^2*y + x*y^2 x^2*y - x*y^2]
4353
4354
sage: R.<x,y> = FreeAlgebra(ZZ,2)
4355
sage: a = matrix(R,2,3,[1,x,y,-x*y,x+y,x-y]); a
4356
[ 1 x y]
4357
[ -x*y x + y x - y]
4358
sage: (x*y) * a # indirect doctest
4359
[ x*y x*y*x x*y^2]
4360
[ -x*y*x*y x*y*x + x*y^2 x*y*x - x*y^2]
4361
"""
4362
# derived classes over a commutative base *just* overload _lmul_ (!!)
4363
if PY_TYPE_CHECK(self._base_ring, CommutativeRing):
4364
return self._lmul_(left)
4365
cdef Py_ssize_t r,c
4366
cpdef RingElement x
4367
x = self._base_ring(left)
4368
cdef Matrix ans
4369
ans = self._parent.zero_matrix().__copy__()
4370
for r from 0 <= r < self._nrows:
4371
for c from 0 <= c < self._ncols:
4372
ans.set_unsafe(r, c, x._mul_(<RingElement>self.get_unsafe(r, c)))
4373
return ans
4374
4375
cpdef ModuleElement _lmul_(self, RingElement right):
4376
"""
4377
EXAMPLES:
4378
4379
A simple example in which the base ring is commutative::
4380
4381
sage: a = matrix(QQ['x'],2,range(6))
4382
sage: a*(3/4)
4383
[ 0 3/4 3/2]
4384
[ 9/4 3 15/4]
4385
4386
An example in which the base ring is not commutative::
4387
4388
sage: F.<x,y> = FreeAlgebra(QQ,2)
4389
sage: a = matrix(2,[x,y,x^2,y^2]); a
4390
[ x y]
4391
[x^2 y^2]
4392
sage: x * a # indirect doctest
4393
[ x^2 x*y]
4394
[ x^3 x*y^2]
4395
sage: a * y
4396
[ x*y y^2]
4397
[x^2*y y^3]
4398
4399
sage: R.<x,y> = FreeAlgebra(ZZ,2)
4400
sage: a = matrix(R,2,3,[1,x,y,-x*y,x+y,x-y]); a
4401
[ 1 x y]
4402
[ -x*y x + y x - y]
4403
sage: a * (x*y)
4404
[ x*y x^2*y y*x*y]
4405
[ -x*y*x*y x^2*y + y*x*y x^2*y - y*x*y]
4406
"""
4407
# derived classes over a commutative base *just* overload this and not _rmul_
4408
cdef Py_ssize_t r,c
4409
cpdef RingElement x
4410
x = self._base_ring(right)
4411
cdef Matrix ans
4412
ans = self._parent.zero_matrix().__copy__()
4413
for r from 0 <= r < self._nrows:
4414
for c from 0 <= c < self._ncols:
4415
ans.set_unsafe(r, c, (<RingElement>self.get_unsafe(r, c))._mul_(x))
4416
return ans
4417
4418
cdef sage.structure.element.Matrix _matrix_times_matrix_(self, sage.structure.element.Matrix right):
4419
r"""
4420
Return the product of two matrices.
4421
4422
EXAMPLE of matrix times matrix over same base ring: We multiply
4423
matrices over `\QQ[x,y]`.
4424
4425
::
4426
4427
sage: R.<x,y> = QQ[]
4428
sage: a = matrix(R,2,3,[1,x,y,-x*y,x+y,x-y]); a
4429
[ 1 x y]
4430
[ -x*y x + y x - y]
4431
sage: b = a.transpose(); b
4432
[ 1 -x*y]
4433
[ x x + y]
4434
[ y x - y]
4435
sage: a*b # indirect doctest
4436
[ x^2 + y^2 + 1 x^2 + x*y - y^2]
4437
[ x^2 + x*y - y^2 x^2*y^2 + 2*x^2 + 2*y^2]
4438
sage: b*a # indirect doctest
4439
[ x^2*y^2 + 1 -x^2*y - x*y^2 + x -x^2*y + x*y^2 + y]
4440
[ -x^2*y - x*y^2 + x 2*x^2 + 2*x*y + y^2 x^2 + x*y - y^2]
4441
[ -x^2*y + x*y^2 + y x^2 + x*y - y^2 x^2 - 2*x*y + 2*y^2]
4442
4443
We verify that the matrix multiplies are correct by comparing them
4444
with what PARI gets::
4445
4446
sage: gp(a)*gp(b) - gp(a*b)
4447
[0, 0; 0, 0]
4448
sage: gp(b)*gp(a) - gp(b*a)
4449
[0, 0, 0; 0, 0, 0; 0, 0, 0]
4450
4451
EXAMPLE of matrix times matrix over different base rings::
4452
4453
sage: a = matrix(ZZ,2,2,range(4))
4454
sage: b = matrix(GF(7),2,2,range(4))
4455
sage: c = matrix(QQ,2,2,range(4))
4456
sage: d = a*b; d
4457
[2 3]
4458
[6 4]
4459
sage: parent(d)
4460
Full MatrixSpace of 2 by 2 dense matrices over Finite Field of size 7
4461
sage: parent(b*a)
4462
Full MatrixSpace of 2 by 2 dense matrices over Finite Field of size 7
4463
sage: d = a*c; d
4464
[ 2 3]
4465
[ 6 11]
4466
sage: parent(d)
4467
Full MatrixSpace of 2 by 2 dense matrices over Rational Field
4468
sage: d = b+c
4469
Traceback (most recent call last):
4470
...
4471
TypeError: unsupported operand parent(s) for '+': 'Full MatrixSpace of 2 by 2 dense matrices over Finite Field of size 7' and 'Full MatrixSpace of 2 by 2 dense matrices over Rational Field'
4472
sage: d = b+c.change_ring(GF(7)); d
4473
[0 2]
4474
[4 6]
4475
4476
EXAMPLE of matrix times matrix where one matrix is sparse and the
4477
other is dense (in such mixed cases, the result is always dense)::
4478
4479
sage: a = matrix(ZZ,2,2,range(4),sparse=True)
4480
sage: b = matrix(GF(7),2,2,range(4),sparse=False)
4481
sage: c = a*b; c
4482
[2 3]
4483
[6 4]
4484
sage: parent(c)
4485
Full MatrixSpace of 2 by 2 dense matrices over Finite Field of size 7
4486
sage: c = b*a; c
4487
[2 3]
4488
[6 4]
4489
sage: parent(c)
4490
Full MatrixSpace of 2 by 2 dense matrices over Finite Field of size 7
4491
4492
EXAMPLE of matrix multiplication over a noncommutative base ring::
4493
4494
sage: R.<x,y> = FreeAlgebra(QQ,2)
4495
sage: x*y - y*x
4496
x*y - y*x
4497
sage: a = matrix(2,2, [1,2,x,y])
4498
sage: b = matrix(2,2, [x,y,x^2,y^2])
4499
sage: a*b
4500
[ x + 2*x^2 y + 2*y^2]
4501
[x^2 + y*x^2 x*y + y^3]
4502
sage: b*a
4503
[ x + y*x 2*x + y^2]
4504
[x^2 + y^2*x 2*x^2 + y^3]
4505
4506
EXAMPLE of row vector times matrix (vectors are row vectors, so
4507
matrices act from the right)::
4508
4509
sage: a = matrix(2,3, range(6)); a
4510
[0 1 2]
4511
[3 4 5]
4512
sage: V = ZZ^2
4513
sage: v = V([-2,3]); v
4514
(-2, 3)
4515
sage: v*a
4516
(9, 10, 11)
4517
4518
This is not allowed, since v is a *row* vector::
4519
4520
sage: a*v
4521
Traceback (most recent call last):
4522
...
4523
TypeError: unsupported operand parent(s) for '*': 'Full MatrixSpace of 2 by 3 dense matrices over Integer Ring' and 'Ambient free module of rank 2 over the principal ideal domain Integer Ring'
4524
4525
This illustrates how coercion works::
4526
4527
sage: V = QQ^2
4528
sage: v = V([-2,3]); v
4529
(-2, 3)
4530
sage: parent(v*a)
4531
Vector space of dimension 3 over Rational Field
4532
4533
EXAMPLE of matrix times column vector: (column vectors are not
4534
implemented yet) TODO TODO
4535
4536
EXAMPLE of scalar times matrix::
4537
4538
sage: a = matrix(2,3, range(6)); a
4539
[0 1 2]
4540
[3 4 5]
4541
sage: b = 3*a; b
4542
[ 0 3 6]
4543
[ 9 12 15]
4544
sage: parent(b)
4545
Full MatrixSpace of 2 by 3 dense matrices over Integer Ring
4546
sage: b = (2/3)*a; b
4547
[ 0 2/3 4/3]
4548
[ 2 8/3 10/3]
4549
sage: parent(b)
4550
Full MatrixSpace of 2 by 3 dense matrices over Rational Field
4551
4552
EXAMPLE of matrix times scalar::
4553
4554
sage: a = matrix(2,3, range(6)); a
4555
[0 1 2]
4556
[3 4 5]
4557
sage: b = a*3; b
4558
[ 0 3 6]
4559
[ 9 12 15]
4560
sage: parent(b)
4561
Full MatrixSpace of 2 by 3 dense matrices over Integer Ring
4562
sage: b = a*(2/3); b
4563
[ 0 2/3 4/3]
4564
[ 2 8/3 10/3]
4565
sage: parent(b)
4566
Full MatrixSpace of 2 by 3 dense matrices over Rational Field
4567
4568
EXAMPLE of scalar multiplication in the noncommutative case::
4569
4570
sage: R.<x,y> = FreeAlgebra(ZZ,2)
4571
sage: a = matrix(2,[x,y,x^2,y^2])
4572
sage: a * x
4573
[ x^2 y*x]
4574
[ x^3 y^2*x]
4575
sage: x * a
4576
[ x^2 x*y]
4577
[ x^3 x*y^2]
4578
sage: a*x - x*a
4579
[ 0 -x*y + y*x]
4580
[ 0 -x*y^2 + y^2*x]
4581
"""
4582
# Both self and right are matrices with compatible dimensions and base ring.
4583
if self._will_use_strassen(right):
4584
return self._multiply_strassen(right)
4585
else:
4586
return self._multiply_classical(right)
4587
4588
cdef bint _will_use_strassen(self, Matrix right) except -2:
4589
"""
4590
Whether or not matrix multiplication of self by right should be
4591
done using Strassen.
4592
4593
Overload _strassen_default_cutoff to return -1 to not use
4594
Strassen by default.
4595
"""
4596
cdef int n
4597
n = self._strassen_default_cutoff(right)
4598
if n == -1:
4599
return 0 # do not use Strassen
4600
if self._nrows > n and self._ncols > n and \
4601
right._nrows > n and right._ncols > n:
4602
return 1
4603
return 0
4604
4605
cdef bint _will_use_strassen_echelon(self) except -2:
4606
"""
4607
Whether or not matrix multiplication of self by right should be
4608
done using Strassen.
4609
4610
Overload this in derived classes to not use Strassen by default.
4611
"""
4612
cdef int n
4613
n = self._strassen_default_echelon_cutoff()
4614
if n == -1:
4615
return 0 # do not use Strassen
4616
if self._nrows > n and self._ncols > n:
4617
return 1
4618
return 0
4619
4620
def __neg__(self):
4621
"""
4622
Return the negative of self.
4623
4624
EXAMPLES::
4625
4626
sage: a = matrix(ZZ,2,range(4))
4627
sage: a.__neg__()
4628
[ 0 -1]
4629
[-2 -3]
4630
sage: -a
4631
[ 0 -1]
4632
[-2 -3]
4633
"""
4634
return self._lmul_(self._base_ring(-1))
4635
4636
def __invert__(self):
4637
r"""
4638
Return this inverse of this matrix, as a matrix over the fraction
4639
field.
4640
4641
Raises a ``ZeroDivisionError`` if the matrix has zero
4642
determinant, and raises an ``ArithmeticError``, if the
4643
inverse doesn't exist because the matrix is nonsquare. Also, note,
4644
e.g., that the inverse of a matrix over `\ZZ` is
4645
always a matrix defined over `\QQ` (even if the
4646
entries are integers).
4647
4648
EXAMPLES::
4649
4650
sage: A = MatrixSpace(ZZ, 2)([1,1,3,5])
4651
sage: ~A
4652
[ 5/2 -1/2]
4653
[-3/2 1/2]
4654
sage: A.__invert__()
4655
[ 5/2 -1/2]
4656
[-3/2 1/2]
4657
4658
Even if the inverse lies in the base field, the result is still a
4659
matrix over the fraction field.
4660
4661
::
4662
4663
sage: I = MatrixSpace(ZZ,2)(1) # identity matrix
4664
sage: ~I
4665
[1 0]
4666
[0 1]
4667
sage: (~I).parent()
4668
Full MatrixSpace of 2 by 2 dense matrices over Rational Field
4669
4670
This is analogous to the situation for ring elements, e.g., for
4671
`\ZZ` we have::
4672
4673
sage: parent(~1)
4674
Rational Field
4675
4676
A matrix with 0 rows and 0 columns is invertible (see trac #3734)::
4677
4678
sage: M = MatrixSpace(RR,0,0)(0); M
4679
[]
4680
sage: M.determinant()
4681
1.00000000000000
4682
sage: M.is_invertible()
4683
True
4684
sage: M.inverse() == M
4685
True
4686
4687
Matrices over the integers modulo a composite modulus::
4688
4689
sage: m = matrix(Zmod(49),2,[2,1,3,3])
4690
sage: type(m)
4691
<type 'sage.matrix.matrix_modn_dense_float.Matrix_modn_dense_float'>
4692
sage: ~m
4693
[ 1 16]
4694
[48 17]
4695
sage: m = matrix(Zmod(2^100),2,[2,1,3,3])
4696
sage: type(m)
4697
<type 'sage.matrix.matrix_generic_dense.Matrix_generic_dense'>
4698
sage: (~m)*m
4699
[1 0]
4700
[0 1]
4701
sage: ~m
4702
[ 1 422550200076076467165567735125]
4703
[1267650600228229401496703205375 422550200076076467165567735126]
4704
4705
This matrix isn't invertible::
4706
4707
sage: m = matrix(Zmod(9),2,[2,1,3,3])
4708
sage: ~m
4709
Traceback (most recent call last):
4710
...
4711
ZeroDivisionError: input matrix must be nonsingular
4712
4713
Check to make sure that trac #2256 is still fixed::
4714
4715
sage: M = MatrixSpace(CC, 2)(-1.10220440881763)
4716
sage: N = ~M
4717
sage: (N*M).norm()
4718
1.0
4719
"""
4720
if not self.base_ring().is_field():
4721
try:
4722
return ~self.matrix_over_field()
4723
except TypeError:
4724
# There is one easy special case -- the integers modulo N.
4725
if is_IntegerModRing(self.base_ring()):
4726
# This is "easy" in that we either get an error or
4727
# the right answer. Note that of course there
4728
# could be a much faster algorithm, e.g., using
4729
# CRT or p-adic lifting.
4730
try:
4731
return (~self.lift()).change_ring(self.base_ring())
4732
except (TypeError, ZeroDivisionError):
4733
raise ZeroDivisionError("input matrix must be nonsingular")
4734
raise
4735
4736
if not self.is_square():
4737
raise ArithmeticError("self must be a square matrix")
4738
if self.nrows()==0:
4739
return self
4740
4741
A = self.augment(self.parent().identity_matrix())
4742
B = A.echelon_form()
4743
4744
# Now we want to make sure that B is of the form [I|X], in
4745
# which case X is the inverse of self. We can simply look at
4746
# the lower right entry of the left half of B, and make sure
4747
# that it's 1.
4748
#
4749
# However, doing this naively causes trouble over inexact
4750
# fields -- see trac #2256. The *right* thing to do would
4751
# probably be to make sure that self.det() is nonzero. That
4752
# doesn't work here, because our det over an arbitrary field
4753
# just does expansion by minors and is unusable for even 10x10
4754
# matrices over CC. Instead, we choose a different band-aid:
4755
# we check to make sure that the lower right entry isn't
4756
# 0. Since we're over a field, we know that it *should* be
4757
# either 1 or 0. This can still cause trouble, but it's
4758
# significantly better than it was before.
4759
#
4760
# Over exact rings, of course, we still want the old
4761
# behavior.
4762
4763
if self.base_ring().is_exact():
4764
if B[self._nrows-1, self._ncols-1] != 1:
4765
raise ZeroDivisionError("input matrix must be nonsingular")
4766
else:
4767
if not B[self._nrows-1, self._ncols-1]:
4768
raise ZeroDivisionError("input matrix must be nonsingular")
4769
4770
return B.matrix_from_columns(range(self._ncols, 2*self._ncols))
4771
4772
def __pos__(self):
4773
"""
4774
Return +self, which is just self, of course.
4775
4776
EXAMPLES::
4777
4778
sage: a = matrix(ZZ,2,range(4))
4779
sage: +a
4780
[0 1]
4781
[2 3]
4782
sage: a.__pos__()
4783
[0 1]
4784
[2 3]
4785
"""
4786
return self
4787
4788
def __pow__(self, n, ignored):
4789
"""
4790
EXAMPLES::
4791
4792
sage: MS = MatrixSpace(QQ, 3, 3)
4793
sage: A = MS([0, 0, 1, 1, 0, '-2/11', 0, 1, '-3/11'])
4794
sage: A * A^(-1) == 1
4795
True
4796
sage: A^4
4797
[ -3/11 -13/121 1436/1331]
4798
[ 127/121 -337/1331 -4445/14641]
4799
[ -13/121 1436/1331 -8015/14641]
4800
sage: A.__pow__(4)
4801
[ -3/11 -13/121 1436/1331]
4802
[ 127/121 -337/1331 -4445/14641]
4803
[ -13/121 1436/1331 -8015/14641]
4804
4805
Sage follows Python's convention 0^0 = 1, as each of the following
4806
examples show::
4807
4808
sage: a = Matrix([[1,0],[0,0]]); a
4809
[1 0]
4810
[0 0]
4811
sage: a^0 # lower right entry is 0^0
4812
[1 0]
4813
[0 1]
4814
sage: Matrix([[0]])^0
4815
[1]
4816
sage: 0^0
4817
1
4818
"""
4819
if not self.is_square():
4820
raise ArithmeticError("self must be a square matrix")
4821
4822
return RingElement.__pow__(self, n, ignored)
4823
4824
###################################################
4825
# Comparison
4826
###################################################
4827
def __hash__(self):
4828
"""
4829
Return the hash of this (immutable) matrix
4830
4831
EXAMPLES::
4832
4833
sage: m=matrix(QQ,2,[1,2,3,4])
4834
sage: m.set_immutable()
4835
sage: m.__hash__()
4836
8
4837
4838
"""
4839
return self._hash()
4840
4841
cdef long _hash(self) except -1:
4842
raise NotImplementedError
4843
4844
cdef int _cmp_c_impl(left,Element right) except -2:
4845
"""
4846
Compare two matrices.
4847
4848
Matrices are compared in lexicographic order on the underlying list
4849
of coefficients. A dense matrix and a sparse matrix are equal if
4850
their coefficients are the same.
4851
4852
EXAMPLES: EXAMPLE comparing sparse and dense matrices::
4853
4854
sage: matrix(QQ,2,range(4)) == matrix(QQ,2,range(4),sparse=True)
4855
True
4856
sage: matrix(QQ,2,range(4)) == matrix(QQ,2,range(4),sparse=True)
4857
True
4858
4859
Dictionary order::
4860
4861
sage: matrix(ZZ,2,[1,2,3,4]) < matrix(ZZ,2,[3,2,3,4])
4862
True
4863
sage: matrix(ZZ,2,[1,2,3,4]) > matrix(ZZ,2,[3,2,3,4])
4864
False
4865
sage: matrix(ZZ,2,[0,2,3,4]) < matrix(ZZ,2,[0,3,3,4], sparse=True)
4866
True
4867
"""
4868
raise NotImplementedError # this is defined in the derived classes
4869
4870
def __nonzero__(self):
4871
"""
4872
EXAMPLES::
4873
4874
sage: M = Matrix(ZZ, 2, 2, [0, 0, 0, 0])
4875
sage: bool(M)
4876
False
4877
sage: M = Matrix(ZZ, 2, 2, [1, 2, 3, 5])
4878
sage: bool(M)
4879
True
4880
"""
4881
cdef Py_ssize_t i, j
4882
for i from 0 <= i < self._nrows:
4883
for j from 0 <= j < self._ncols:
4884
if self.get_unsafe(i,j):
4885
return True
4886
return False
4887
4888
cdef int _strassen_default_cutoff(self, Matrix right) except -2:
4889
return -1
4890
4891
cdef int _strassen_default_echelon_cutoff(self) except -2:
4892
return -1
4893
4894
4895
4896
4897
#######################
4898
# Unpickling
4899
#######################
4900
4901
def unpickle(cls, parent, immutability, cache, data, version):
4902
r"""
4903
Unpickle a matrix. This is only used internally by Sage. Users
4904
should never call this function directly.
4905
4906
EXAMPLES: We illustrating saving and loading several different
4907
types of matrices.
4908
4909
OVER `\ZZ`::
4910
4911
sage: A = matrix(ZZ,2,range(4))
4912
sage: loads(dumps(A)) # indirect doctest
4913
[0 1]
4914
[2 3]
4915
4916
Sparse OVER `\QQ`:
4917
4918
Dense over `\QQ[x,y]`:
4919
4920
Dense over finite field.
4921
"""
4922
cdef Matrix A
4923
A = cls.__new__(cls, parent, 0,0,0)
4924
A._parent = parent # make sure -- __new__ doesn't have to set it, but unpickle may need to know.
4925
A._nrows = parent.nrows()
4926
A._ncols = parent.ncols()
4927
A._is_immutable = immutability
4928
A._base_ring = parent.base_ring()
4929
A._cache = cache
4930
if version >= 0:
4931
A._unpickle(data, version)
4932
else:
4933
A._unpickle_generic(data, version)
4934
return A
4935
4936
4937
max_rows = 20
4938
max_cols = 50
4939
4940
def set_max_rows(n):
4941
"""
4942
Sets the global variable max_rows (which is used in deciding how to output a matrix).
4943
4944
EXAMPLES::
4945
4946
sage: from sage.matrix.matrix0 import set_max_rows
4947
sage: set_max_rows(20)
4948
4949
"""
4950
4951
global max_rows
4952
max_rows = n
4953
4954
def set_max_cols(n):
4955
"""
4956
Sets the global variable max_cols (which is used in deciding how to output a matrix).
4957
4958
EXAMPLES::
4959
4960
sage: from sage.matrix.matrix0 import set_max_cols
4961
sage: set_max_cols(50)
4962
4963
"""
4964
4965
global max_cols
4966
max_cols = n
4967
4968