In this tutorial we demonstrate the use of structured dense matrices (Circulant matrix, Hankel matrix, Toeplitz matrix, Vandermonde matrix).
- Warning
- Structured matrices in ViennaCL are experimental and only available with the OpenCL backend.
We start with including the necessary headers: 
#include <iostream>
#include "boost/numeric/ublas/vector.hpp"
#include "boost/numeric/ublas/matrix.hpp"
#include "boost/numeric/ublas/matrix_proxy.hpp"
#include "boost/numeric/ublas/io.hpp"
  We first setup the respective matrices in uBLAS matrices and then copy them over to the respective ViennaCL objects. After that we run a couple of operations (mostly matrix-vector products). 
 Set up ublas objects 
boost::numeric::ublas::vector<ScalarType> ublas_vec(size);
boost::numeric::ublas::matrix<ScalarType> ublas_circulant(size, size);
boost::numeric::ublas::matrix<ScalarType> ublas_hankel(size, size);
boost::numeric::ublas::matrix<ScalarType> ublas_toeplitz(size, size);
boost::numeric::ublas::matrix<ScalarType> ublas_vandermonde(size, size);
for (std::size_t i = 0; i < 
size; i++)
 
  for (std::size_t j = 0; j < 
size; j++)
 
  {
    ublas_circulant(i,j)   = 
static_cast<ScalarType
>((i - j + 
size) % size);
    ublas_hankel(i,j)      = static_cast<ScalarType>((i + j) % (2 * size));
    ublas_toeplitz(i,j)    = static_cast<ScalarType>(i) - static_cast<ScalarType>(j);
  }
 Set up ViennaCL objects 
for (std::size_t i = 0; i < 
size; i++)
 
{
}
  Add circulant matrices using operator overloads: 
std::cout << "Circulant matrix before addition: " << vcl_circulant << std::endl << std::endl;
vcl_circulant += vcl_circulant;
std::cout << "Circulant matrix after addition: " << vcl_circulant << std::endl << std::endl;
 Manipulate single entries of structured matrices. These manipulations are structure-preserving, so any other affected entries are manipulated as well. 
std::cout << "Hankel matrix before manipulation: " << vcl_hankel << std::endl << std::endl;
std::cout << "Hankel matrix after manipulation: " << vcl_hankel << std::endl << std::endl;
std::cout << "Vandermonde matrix before manipulation: " << vcl_vandermonde << std::endl << std::endl;
std::cout << "Vandermonde matrix after manipulation: " << vcl_vandermonde << std::endl << std::endl;
 Compute matrix-vector product for a Toeplitz matrix (FFT-accelerated). Similarly for the other matrices. 
std::cout << "Toeplitz matrix: " << vcl_toeplitz << std::endl;
std::cout << "Vector: " << vcl_vec << std::endl << std::endl;
std::cout << "Result of matrix-vector product: " << vcl_result << std::endl << std::endl;
 That's it. Print success message and exit. 
  std::cout << "!!!! TUTORIAL COMPLETED SUCCESSFULLY !!!!" << std::endl;
  return EXIT_SUCCESS;
}
Full Example Code
#include <iostream>
#include "boost/numeric/ublas/vector.hpp"
#include "boost/numeric/ublas/matrix.hpp"
#include "boost/numeric/ublas/matrix_proxy.hpp"
#include "boost/numeric/ublas/io.hpp"
{
  std::size_t size = 4;
  boost::numeric::ublas::vector<ScalarType> ublas_vec(size);
  boost::numeric::ublas::matrix<ScalarType> ublas_circulant(size, size);
  boost::numeric::ublas::matrix<ScalarType> ublas_hankel(size, size);
  boost::numeric::ublas::matrix<ScalarType> ublas_toeplitz(size, size);
  boost::numeric::ublas::matrix<ScalarType> ublas_vandermonde(size, size);
  for (std::size_t i = 0; i < 
size; i++)
 
    for (std::size_t j = 0; j < 
size; j++)
 
    {
      ublas_circulant(i,j)   = 
static_cast<ScalarType
>((i - j + 
size) % size);
      ublas_hankel(i,j)      = static_cast<ScalarType>((i + j) % (2 * size));
      ublas_toeplitz(i,j)    = static_cast<ScalarType>(i) - static_cast<ScalarType>(j);
    }
  
  
  for (std::size_t i = 0; i < 
size; i++)
 
  {
  }
  std::cout << "Circulant matrix before addition: " << vcl_circulant << std::endl << std::endl;
  vcl_circulant += vcl_circulant;
  std::cout << "Circulant matrix after addition: " << vcl_circulant << std::endl << std::endl;
  std::cout << "Hankel matrix before manipulation: " << vcl_hankel << std::endl << std::endl;
  std::cout << "Hankel matrix after manipulation: " << vcl_hankel << std::endl << std::endl;
  std::cout << "Vandermonde matrix before manipulation: " << vcl_vandermonde << std::endl << std::endl;
  std::cout << "Vandermonde matrix after manipulation: " << vcl_vandermonde << std::endl << std::endl;
  std::cout << "Toeplitz matrix: " << vcl_toeplitz << std::endl;
  std::cout << "Vector: " << vcl_vec << std::endl << std::endl;
  std::cout << "Result of matrix-vector product: " << vcl_result << std::endl << std::endl;
  std::cout << "!!!! TUTORIAL COMPLETED SUCCESSFULLY !!!!" << std::endl;
  return EXIT_SUCCESS;
}