Subspaces and Dimension

Amazingly, Sage knows what a linear subspace is, and can do basic computations with them. (Why is this amazing? This is a fairly abstract concept to implement on a computer. You can reduce most computations involving subspaces to computations about matrices. Usually, I would expect a human would do that reduction, and then ask a computer to do the matrix computation. Being able to offload both parts, rather than just the second, to the computer is nice, though Sage’s implementation of the concept is not terribly robust.)

We’ve been working with null spaces, column spaces, row spaces, and spans. These work how you would expect in Sage, except with a few twists:

  • It’s important to specify where the entries of the matrices live, i.e., that they are rational numbers or real numbers. We will work with rational numbers in this post; to work with real numbers, replace “QQ” by “RR” below. (Subspaces work differently over the integers than over the rationals or reals.)
  • The null space is also called the kernel, and Sage uses the word kernel.
  • Sage defaults to finding the left kernel of a matrix, i.e., vectors v so that vM=0. In class, we always look at the right kernel, so we have to tell Sage we want the right_kernel.
  • Getting Sage to create the span of a list of vectors seems to be tricky. Just make those vectors into the columns of a matrix and use the column space instead.

With this in mind, let’s create some subspaces. Let’s start with the column space and row space:
M = matrix(QQ,[[1,2,3],[4,5,6],[5,7,9],[3,6,9]])
M
C = M.column_space()
C

Sage tells you the dimension of the ambient space (4) and the subspace (2).

ColSpace1

The output is actually quite different if you turn on typeset_mode:

%typeset_mode True
C

ColSpace2

In both cases, Sage is telling you that a basis for the subspace is given by the transposes of (1,0,1,3) and (0,1,1,0). (Sage likes row vectors.) We can get a basis explicitly, as a list of vectors:
C.basis()
C.dimension()
ColSpace3

Row space is just the same, but with column_space replaced by row_space:

R = M.row_space()
R
R.basis()

Next, for the null space, remember the points above.
K = M.right_kernel()
K
K.basis()
Kernel1

Let’s check that this vector really is in the kernel (null space). This is a little tricky: the basis() command returned a list of vectors, with one vector fin it. We have to extract the vector from the list:
v = K.basis()[0]
v
M*v

Kernel2

In case that was confusing, here’s another kernel example:
N = matrix(QQ,[[1,2,3,4,5],[6,7,8,9,10]])
K_new = N.right_kernel()
list_of_vectors = K_new.basis()
list_of_vectors

We can pick out the individual elements of list_of_vectors:
list_of_vectors[0]
list_of_vectors[1]
list_of_vectors[2]
Kernel3

Let’s check some of these are, indeed, in the null space:
N * list_of_vectors[0]
N * list_of_vectors[1]

Kernel4

(If you’ve programmed in Python before, you should be able to check that all of the vectors are in the null space in a single line of code…)

Post a Comment

Your email address is never published nor shared. Required fields are marked *

*
*

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>

Skip to toolbar