3. Matrix Manipulation

Once a matrix or an array has been defined it might be necessary to either extract some submatrices from the matrix, to reshape it, i.e. change its dimensions, or to modify the order of its elements. You find all the following examples in 1774matrix04.xpl and 1777matrix05.xpl.


3.1 Extraction of Elements


y = x[i,j] or y = x[i,] or y = x[,j]
extracts element i,j or row i or column j from x
y = 1835 index (x, ind)
generates a new matrix y from an old matrix x by extracting the rows of x indicated in the index vector ind
y = 1838 paf (x, ind)
selects rows of an object x depending on a given vector ind resulting in the matrix y
y = 1841 sort (x, c)
sorts the rows of a matrix x by the vector c

We extract elements or submatrices of a matrix with the operator []. Consider the 4 x 3 matrix


  mat=(1|2|3|4)~(5|6|7|8)~(9|9|9|9)

The following three lines extract respectively the first row, the second column, and the element in the fourth row and third column:

  mat[1,]                  ; extract first row

  mat[,2]                  ; extract second column

  mat[4,3]                 ; extract element (4,3)

The [] operator can be combined with the range operator, denoted by the colon symbol :, and the | operator. The command


  mat[1:3,1|3]

extracts the elements which are between the first and the third rows of mat and in the 1st and 3rd columns.

In a similar way, we extract certain rows from a matrix with the function 1848 index. Its first argument is the matrix, its second argument is the index of the considered rows. This second argument can be a vector of indices. In that case, all rows which are in the index vector are extracted. The instructions


  x = #(1,3,5)~#(2,4,6)

  index (x,#(3,2))

create a 3 x 2 matrix, and respectively extract its third and second rows:

  Contents of index

  [1,]        5        6

  [2,]        3        4

Note that index(x,#(3,2)) is identical to x[#(3,2)] as long as the values in the index vector -- here #(3,2) -- do not exceed the dimension of x. If this is the case, x[#(3,2)] would return an error message while the 1851 index function returns NaN values.

We can select rows of a matrix on the basis of a logical condition with the function 1854 paf. The first argument of the function is the matrix, the second argument is an indicator vector with the same row dimension as the matrix. The function 1857 paf selects the rows of the matrix whose corresponding element in the indicator vector is different from zero. Note that 1860 paf returns an error, if no element of the indicator vector is different from zero!

The following example illustrates the use of this function:


  x = #(4, 2, 5)

  ind = x > 3

  paf(x, ind)

The three-dimensional vector x and the three-dimensional indicator vector ind are created. Since the vector ind is created with the logical condition x > 3, its elements are either equal to 1 if the corresponding element of the vector x is strictly greater than 3, or to zero otherwise. As only the second element of x is less than 3, the second element of ind is set to zero, the function 1863 paf selects the remaining first and third rows of x and returns them:

  Contents of paf

  [1,]        4 

  [2,]        5

The function 1866 sort sorts the rows of a matrix. Its first argument is the matrix, its second argument is the column with respect to which the sorting is done. If this column order is positive, the matrix will be sorted by that column in ascending order, while if the column order is negative, the matrix will be sorted in descending order. The column order can be a vector. In that case, the matrix is first sorted by the first element of the sorting vector, next the matrix is sorted by the second element of the sorting vector provided that this second sorting does not modify the previous one. The instructions


  x = #(4,2,5)~#(1,7,4)

  x

  sort(x,-2)

create a 3 x 2 matrix. Since the second argument of 1869 sort is equal to -2, this matrix is sorted in descending order by the second column:

  Contents of x

  [1,]        4        1 

  [2,]        2        7 

  [3,]        5        4 

  Contents of sort

  [1,]        2        7 

  [2,]        5        4 

  [3,]        4        1

If the second argument of the function 1872 sort is set to 0, all columns of the matrix are independently sorted in ascending order. This means,

  sort(x,0)

gives

  Contents of sort

  [1,]        2        1 

  [2,]        4        4 

  [3,]        5        7

Let us remark that all functions from this section can also be applied to alphanumeric matrices. Also, the extension to higher-dimensional arrays is straightforward.


3.2 Matrix Transformation


y = 1894 reduce (x)
deletes all dimensions of x with only a single component
y = 1897 reshape (x, d)
transforms an array x into a new one y with given dimensions d
y = 1900 vec (x1 {,x2 ...})
vectorizes the arrays x1, x2, ...

If some of the dimensions of a multidimensional matrix are equal to one, we can discard them with the function 1903 reduce. Since this function is part of the library xplore, this library should be loaded before the use of the function. The commands


  library("xplore")

  x = matrix(3,1,2,1)

  reduce(x)

create a 3 x 1 x 2 x 1 matrix of ones, discard the two dimensions equal to one, and leave a 3 x 2 matrix which is displayed as follows:

  Contents of y

  [1,]        1        1 

  [2,]        1        1 

  [3,]        1        1

The dimensions of an array can be modified with the function 1908 reshape although the modified array does contain the same number of elements as the original array. The first argument of the function is the array to be modified, i.e. the source array, the second argument is the dimension of the target array. The function 1911 reshape reads rowwise the elements of the source array and stores them rowwise into the target array. The commands


  x = #(1, 1, 1, 1, 1)~#(2, 2, 2, 2, 2)

  x

  d = #(2, 5)   

  reshape(x, d)

create a 5 x 2 matrix, display it, reshape it into a 2 x 5 matrix, and display it:

  Contents of x

  [1,]        1        2

  [2,]        1        2

  [3,]        1        2

  [4,]        1        2

  [5,]        1        2

  Contents of reshape

  [1,]        1        1        1        2        2

  [2,]        1        1        2        2        2

The function 1914 vec reshapes a matrix into a vector:


  vec(x)

yields

  Contents of #

  [ 1,]        1 

  [ 2,]        1 

  [ 3,]        1 

  [ 4,]        1 

  [ 5,]        1 

  [ 6,]        2 

  [ 7,]        2 

  [ 8,]        2 

  [ 9,]        2 

  [10,]        2

The 1917 vec function can optionally add some elements to the reshaped vector:

  vec(x,5)~vec(3,x)

returns

  Contents of _tmp

  [ 1,]        1        3 

  [ 2,]        1        1 

  [ 3,]        1        1 

  [ 4,]        1        1 

  [ 5,]        1        1 

  [ 6,]        2        1 

  [ 7,]        2        2 

  [ 8,]        2        2 

  [ 9,]        2        2 

  [10,]        2        2 

  [11,]        5        2

The instruction vec(x,5) reshapes the matrix x into a vector and adds the number 5 as the last element of the created vector. However, since the number 3 is the first argument of the function 1920 vec in the instruction vec(3,x), the first element of the created vector is this number to which the ``vectorized'' matrix is added.

As a consequence, both instructions


  z1 = #(1,2,3)

  z2 = vec(1,2,3)

are equivalent.



Method and Data Technologies   MD*TECH Method and Data Technologies
  http://www.mdtech.de  mdtech@mdtech.de