PARP Research Group Universidad de Murcia

Matrices and vectors

In the QVision framework, matrices and vectors are represented as objects. These objects are created from the QVMatrix and QVVector classes respectively.

They offer constructors, operators and methods to perform several operations.

Matrix and vector initialization

The QVMatrix and QVVector classes have several constructors. The matrix default constructor creates a 1x1 size matrix:

// Creates a 1x1 matrix
QVMatrix A;

while the default constructor for the QVVector class creates an empty vector:

// Creates an empty vector
QVVector v;

These constructors are useful for completeness. Another constructor creates matrices and vectors specifying their size, and a default value for their content values:

// Creates a matrix of size 3x4, containing the value 1.0 in every element.
QVMatrix A(3, 4, 1.0);

// Creates a vector of size 5, containing the value 2.0 in every element.
QVVector v(5, 2.0);

You can omit the default value, to create matrices and vectors with uninitialized contents:

// Creates a matrix of size 3x4, containing unspecified element values.
QVMatrix A(3, 4);

// Creates a vector of size 5, containing unspecified element values.
QVVector v(5);

There is a constructor to initialize the matrix and vector elements from a C array of double values:

double  matrix_values[12] = { 1.0, 2.0, 3.0, 4.0, 5.0, 6.0, 7.0, 8.0, 9.0, 10.0, 11.0, 12.0 },
        vector_values[5] = { 1.0, 2.0, 3.0, 4.0, 5.0 };

// Creates a matrix containing the values of the array 'matrix_values', in row order.
QVMatrix A2(3,4, matrix_values);

// Creates a vector containing the values of the array 'vector_values'.
QVVector v2(5, vector_values);

A QVMatrix can also be initialized from a QVVector. Since QVVector itself inherits from QVector, which in turn can be populated with elements using the << operator, the following code is perfectly valid to initialize aa 4x4 matrix:

    A = QVMatrix(4,4,QVVector() << 1 << 2 << 3 << 4
                                << 2 << 3 << 4 << 5
                                << 3 << 4 << 5 << 6
                                << 4 << 5 << 6 << 7);

You can also convert a QVVector to a QVMatrix (as row or as column):

    A = QVMatrix(QVVector() << 1 << 2 << 3,true);
    std::cout << "Matrix A:" << A << "\n";
    A = QVMatrix(QVVector() << 1 << 2 << 3,false);
    std::cout << "Matrix A:" << A << "\n";

There are also adequate conversions for gsl_matrix, gsl_vector (GSL) and a CvMat (OpenCV). See reference documentation of the QVMatrix and QVVector for details.

A list of QPointF's (also of QVVector's, QVector<double>) can be directly used to initialize a QVMatrix:

    A = QList<QPointF>() << QPointF(1,2) << QPointF(2,3) << QPointF(3,4) << QPointF(4,5);
    std::cout << "Matrix A:" << A << "\n";

You can also convert a matrix to a list of QVVectors (also QVVector's, QVector<double>):

    QList<QVVector> list = A;
    foreach(QVVector v,list) {
        std::cout << "vector=" << v << "\n" ;

And you can also initialize a rotation matrix from a QVQuaternion:

    // A = QVQuaternion(); // Deprecated, but still valid.
    QVQuaternion q; // Equivalent.
    std::cout << "Quaternion q:" << q << "\n";
    A = q.toRotationMatrix();
    std::cout << "Matrix A:" << A << "\n";

A last kind of constructor is the copy constructor. These constructors initialize the contents of a matrix, or a vector, from the contents of another matrix, or vector:

// Matrix 'A3' will replicate the size and contents of matrix 'A'.
QVMatrix A3 = A;

// Vector 'v3' will replicate the size and contents of vector 'v'.
QVVector v3 = v;

Accessing the elements of matrices and vectors

The matrix and vectors elements can be accessed with the operator ():

// Create a matrix of size 3x4, with its elements uninitialized.
QVMatrix A4(3,4);

// Initialize each element 'i,j' of the matrix, to the value 'i*j'
for(int i = 0; i < 3; i++)
        for(int i = 0; i < 4; i++)
                A4(i,j) = i*j;

// Create a vector of size 4, with its elements uninitialized.
QVVector v4[4];

// Copy the last column of matrix 'A4' in the vector 'v4', element by element.
for(int i = 0; i < 4; i++)
        v4(i) = A4(2,j);
In the case of QVVectors, the [] access operator is also available, and can be faster than the () operator.

Storing and loading matrices to/from files.

A matrix can be stored in a file, in a plain text format, using the functions readQVMatrixFromFile and writeQVMatrixToFile. These functions can read or write only a matrix, from a single file. An example usage of these functions is the following:

// Creates a random matrix of size 3x4
QVMatrix M = QVMatrix::random(3,4);

// Stores that matrix in the file 'test.txt'.
writeQVMatrixToFile("test.txt", M);

// Retrieve the matrix stored in file 'test.txt', in matrix variable 'M2'.
QVMatrix M2;
readQVMatrixFromFile("test.txt", M2);

That code stores in a text file of name test.txt a randomly initialized matrix of 3x4 elements. The text file will contain something like the following text, describing the matrix saved in the file:

QVMatrix (3, 4)
    [ 0.128115 0.968417 0.053520 0.024858 ]
    [ 0.856481 0.031511 0.710598 0.217373 ]
    [ 0.892742 0.400330 0.548256 0.519458 ]

Matrix appending operators

Two matrices of size mxn and pxn can be appended vertically using the ampersand operator &, to create a matrix of size (m+p)xn:

QVMatrix A(10,20), B(7, 20);

// Init the contents of 'A' and 'B'
[ ... ]

QVMatrix C = A & B;

The resulting content of the matrix C can be expressed with the following equation:

$ C = \left( \begin{array}{c} A \\ B \\ \end{array} \right) $

Similarly, the pipe operator | can be used to append horizontally two matrices of size nxm and nxp, to create a new matrix of size nx(m+p):

QVMatrix A(20,10), B(20, 7);

// Init the contents of 'A' and 'B'
[ ... ]

QVMatrix C = A | B;

The resulting content of the matrix C can be expressed with the following equation:

$ C = \left( \begin{array}{cc} A & B \\ \end{array} \right) $

The following is an extended example, which appends several matrices, to create the following matrix:

$ C = \left( \begin{array}{c|c} I & 0 \\ \hline 0 & A \\ \end{array} \right) $

QVMatrix A(4,4);

// Init the contents of 'A'
[ ... ]

QVMatrix C =    ( QVMatrix::identity(3) | QVMatrix(3,4,0.0) ) &
                ( QVMatrix(4,3,0.0)     | A                 );

Aritmetical operators for matrices and vectors

Matrices and vectors redefine the following arithmetical operators: +, -, *, /, and ^. They can be used to naturally operate with matrices, vectors, and scalar numbers.

// Create matrix 'A' of size 3x3, and containing random values.
QVMatrix        A = QVMatrix::random(3,3),
                B = QVMatrix::random(3,3);

// Multiply 'A' and 'B' matrices.
std::cout << A*B << std::endl;

// Solve 'X' in the linear equation system
//      XB = A
// Where 'X' is a 3x3 matrix.
std::cout << A/B << std::endl;

// Add the elements of both matrices 'A' and 'B'.
std::cout << A+B << std::endl;

// Multiply each element of 'A' by the scalar value 2.0.
std::cout << A*2.0 << std::endl;
std::cout << 2.0*A << std::endl;

// Add scalar 2.0 to every element of the matrix 'A'.
std::cout << 2.0 + A << std::endl;
std::cout << A + 2.0  << std::endl;

// Create randomly initialized vectors.
QVVector v = QVMatrix::random(3,1), w = QVMatrix::random(3,1);

// Multiply the matrix 'A' by the column vector 'v'.
// Matrix 'A' must have the same number of columns, than the size of vector 'v'.
std::cout << A*v << std::endl;

// Multiply the row vector 'v' by the matrix 'A'.
// Matrix 'A' must have the same number of rows, than the size of vector 'v'.
std::cout << v*A << std::endl;

// Perform scalar product of vectors 'v' and 'w'.
std::cout << v*w << std::endl;

// Obtain vector product of vectors 'v' and 'w' (only for vectors of dimension 3).
std::cout << v^w << std::endl;

Other operations with matrices and vectors.

Besides the standard arithmetic operations, the library also offers many other typical operations for matrices/vectors:

  • For matrices: generation of random, zeros, identity and diagonal matrices, 2D and 3D rotation / scale / translation matrices; transpose operation, norm and trace of a matrix, reshaping (same data, new dimensions), submatrix extraction, determinant, etc.
  • For vectors: random, gauss and mexican hat vector generation, subvector extraction, max / min / mean / median / sum / variance / enthropy of the elements of the vector,

See reference documentation of classes QVMatrix and QVVector for details.

Matrix factorizations

The QVision offers wrapper functions to most of the GSL and Lapack (MKL versions) matrix factorization routines. Take a look at the module Matrix Algebra for a comprehensive list of these matrix decomposition methods.

QVision framework. PARP research group. Copyright © 2007, 2008, 2009, 2010, 2011.