ublas_plus.h.html |
mathcode2html
|
Source file: ublas_plus.h
|
Converted: Sun Aug 7 2016 at 13:45:52
|
This documentation file will
not reflect any later changes in the source file.
|
$$\phantom{******** If you see this on the webpage then the
browser could not locate *********}$$
$$\phantom{******** jsMath/easy/load.js or the variable root
is set wrong in this file *********}$$
$$\newcommand{\vector}[1]{\left[\begin{array}{c} #1 \end{array}\right]}$$
$$\newenvironment{matrix}{\left[\begin{array}{cccccccccc}} {\end{array}\right]}$$
$$\newcommand{\A}{{\cal A}}$$
$$\newcommand{\W}{{\cal W}}$$
/* Copyright 2008-2014 Research Foundation State University of New York */
/* This file is part of QUB Express. */
/* QUB Express is free software; you can redistribute it and/or modify */
/* it under the terms of the GNU General Public License as published by */
/* the Free Software Foundation, either version 3 of the License, or */
/* (at your option) any later version. */
/* QUB Express is distributed in the hope that it will be useful, */
/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
/* GNU General Public License for more details. */
/* You should have received a copy of the GNU General Public License, */
/* named LICENSE.txt, in the QUB Express program directory. If not, see */
/* <http://www.gnu.org/licenses/>. */
#ifndef UBLAS_PLUS_H
#define UBLAS_PLUS_H
/*
*/
// This header includes the vector and matrix from boost::ublas,
// and defines template functions to set up, read, print, and store them.
#include <boost/numeric/ublas/vector.hpp>
#include <boost/numeric/ublas/matrix.hpp>
#include <algorithm>
#include <vector>
#include "qubfast.h"
using namespace boost::numeric::ublas;
using std::min;
using std::max;
template<class S, class T>
void matrix_from_arrays(matrix<S>& mat, T** dat, int m, int n)
{
if ( mat.size1() != (size_t) m || mat.size2() != (size_t) n )
mat.resize(m, n);
for (int i=0; i<m; ++i) {
S* mat_i = & mat(i, 0);
T* dat_i = dat[i];
for (int j=n; j; --j)
*(mat_i++) = (S) *(dat_i++);
}
/* some compilers can't handle these templates:
// typename M::iterator1; // so the compiler doesn't treat it as R-value
typename M::iterator1 mat_i = mat.begin1();
for (int i=0; i<m; ++i, ++mat_i) {
#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
typename M::iterator2 mat_j = mat_i.begin();
#else
typename M::iterator2 mat_j = begin(mat_i, iterator1_tag());
#endif
T* dat_j = dat[i];
for (int j=0; j<n; ++j)
*(mat_j++) = *(dat_j++);
}
*/
}
template<class S, class T>
void matrix_to_arrays(matrix<S>& mat, T** dat, int m, int n)
{
for (int i=0; i<m; ++i) {
S* mat_i = & mat(i, 0);
T* dat_i = dat[i];
for (int j=n; j; --j)
*(dat_i++) = (T) *(mat_i++);
}
/* some compilers can't handle these templates:
typename M::iterator1 mat_i = mat.begin1();
for (int i=0; i<m; ++i, ++mat_i) {
#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
typename M::iterator2 mat_j = mat_i.begin();
#else
typename M::iterator2 mat_j = begin(mat_i, iterator1_tag());
#endif
T* dat_j = dat[i];
for (int j=0; j<n; ++j)
*(dat_j++) = *(mat_j++);
}
*/
}
template<class S, class T>
void matrix_from_array(matrix<S>& mat, T* dat, int m, int n)
{
if ( mat.size1() != (size_t) m || mat.size2() != (size_t) n )
mat.resize(m, n);
T* dat_i = dat;
for (int i=0; i<m; ++i) {
S* mat_i = & mat(i, 0);
for (int j=n; j; --j)
*(mat_i++) = (S) *(dat_i++);
}
// typename M::iterator1; // so the compiler doesn't treat it as R-value
/* some compilers can't handle these templates:
typename M::iterator1 mat_i = mat.begin1();
for (int i=0; i<m; ++i, ++mat_i) {
#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
typename M::iterator2 mat_j = mat_i.begin();
#else
typename M::iterator2 mat_j = begin(mat_i, iterator1_tag());
#endif
for (int j=0; j<n; ++j) {
*(mat_j++) = *(dat_i++);
}
}
*/
}
template<class S, class T>
void matrix_to_array(matrix<S>& mat, T* dat, int m, int n)
{
int M = min(m, (int) mat.size1());
int N = min(n, (int) mat.size2());
int i, j;
for (i=0; i<M; ++i) {
S *mat_i = & mat(i, 0);
for (j=0; j<N; ++j)
*(dat++) = (T) *(mat_i++);
for (; j<n; ++j)
*(dat++) = 0.0;
}
for (; i<m; ++i)
for (j=0; j<m; ++j)
*(dat++) = 0.0;
}
template<class T>
void matrix_to_partition(matrix<T>& mat, int m, int n, int *rowix, int *colix, matrix<T>& part)
{
if ( part.size1() != (size_t) m || part.size2() != (size_t) n )
part.resize(m, n);
for (int i=0; i<m; ++i)
for (int j=0; j<n; ++j)
part(i,j) = mat(rowix[i], colix[j]);
}
template<class T>
void matrix_from_partition(matrix<T>& mat, int m, int n, int *rowix, int *colix, matrix<T>& part)
{
if ( part.size1() != (size_t) m || part.size2() != (size_t) n )
part.resize(m, n);
for (int i=0; i<m; ++i)
for (int j=0; j<n; ++j)
mat(rowix[i], colix[j]) = part(i,j);
}
template<class T>
void fill_identity(matrix<T>& mat)
{
int m = (int) mat.size1();
int n = (int) mat.size2();
for (int i=0; i<m; ++i)
for (int j=0; j<n; ++j)
mat(i,j) = (i==j) ? 1 : 0;
}
template<class T>
void fill_const(matrix<T>& mat, T val)
{
for (typename matrix<T>::iterator1 ii = mat.begin1(); ii != mat.end1(); ++ii)
#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
for (typename matrix<T>::iterator2 jj = ii.begin(); jj != ii.end(); ++jj)
#else
for (typename matrix<T>::iterator2 jj = begin(ii, iterator1_tag()); jj != end(ii, iterator1_tag()); ++jj)
#endif
*jj = val;
}
template<class T>
std::ostream& operator<<(std::ostream& ost, vector<T>& vec)
{
ost << "[ ";
for (typename vector<T>::iterator ii = vec.begin(); ii != vec.end(); ++ii)
ost << *ii << ' ';
ost << "]";
return ost;
}
template<class T>
std::ostream& operator<<(std::ostream& ost, matrix<T>& mat)
{
ost << "[ ";
for (typename matrix<T>::iterator1 ii = mat.begin1(); ii != mat.end1(); ++ii) {
ost << "[ ";
#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
for (typename matrix<T>::iterator2 jj = ii.begin(); jj != ii.end(); ++jj) {
#else
for (typename matrix<T>::iterator2 jj = begin(ii, iterator1_tag()); jj != end(ii, iterator1_tag()); ++jj) {
#endif
ost << *jj << ' ';
}
ost << "]" << std::endl << " ";
}
ost << "]";
return ost;
}
// These are to simplify working with C-interfaced code, which variously expects T* or T**
// e.g. in max_mac_ll.cpp
template<class T> class pointy_matrix {
public:
matrix<T> m;
std::vector<T*> rows;
T *p, **pp;
int n; // == m.size1() * m.size2()
pointy_matrix()
: p(NULL), pp(NULL), n(0)
{}
pointy_matrix(int nr, int nc)
: m(nr, nc), rows(nr), p(NULL), pp(NULL), n(nr*nc)
{
resize(nr, nc);
}
void resize(int nr, int nc)
{
n = nr*nc;
m.resize(nr, nc);
m.clear();
rows.resize(nr);
for (int i=0; i<nr; ++i)
rows[i] = &(m(i,0));
if ( nr && nc ) {
p = &(m(0,0));
pp = &(rows[0]);
}
}
void clear()
{
m.clear();
}
};
template<class T>
class pointy_col_vector {
public:
matrix<T> m;
T *p, **pp;
int n;
pointy_col_vector()
: p(NULL), pp(&p), n(0)
{}
pointy_col_vector(int _n)
: m(_n,1), p(NULL), pp(&p), n(_n)
{
resize(_n);
}
pointy_col_vector(int _n, T *data)
: m(_n,1), p(NULL), pp(&p), n(_n)
{
resize(_n);
memcpy(p, data, _n*sizeof(T));
}
void resize(int _n)
{
n = _n;
m.resize(_n,1);
m.clear();
if ( _n )
p = &(m(0,0));
}
void clear()
{
m.clear();
}
};
#ifdef _WIN32
QUBFAST_TEMPLATE template class QUBFAST_API boost::numeric::ublas::vector<char>;
QUBFAST_TEMPLATE template class QUBFAST_API boost::numeric::ublas::matrix<char>;
QUBFAST_TEMPLATE template class QUBFAST_API boost::numeric::ublas::vector<short>;
QUBFAST_TEMPLATE template class QUBFAST_API boost::numeric::ublas::matrix<short>;
QUBFAST_TEMPLATE template class QUBFAST_API boost::numeric::ublas::vector<int>;
QUBFAST_TEMPLATE template class QUBFAST_API boost::numeric::ublas::matrix<int>;
QUBFAST_TEMPLATE template class QUBFAST_API boost::numeric::ublas::vector<float>;
QUBFAST_TEMPLATE template class QUBFAST_API boost::numeric::ublas::matrix<float>;
QUBFAST_TEMPLATE template class QUBFAST_API boost::numeric::ublas::vector<double>;
QUBFAST_TEMPLATE template class QUBFAST_API boost::numeric::ublas::matrix<double>;
QUBFAST_TEMPLATE template class QUBFAST_API pointy_matrix<char>;
QUBFAST_TEMPLATE template class QUBFAST_API pointy_matrix<short>;
QUBFAST_TEMPLATE template class QUBFAST_API pointy_matrix<int>;
QUBFAST_TEMPLATE template class QUBFAST_API pointy_matrix<float>;
QUBFAST_TEMPLATE template class QUBFAST_API pointy_matrix<double>;
QUBFAST_TEMPLATE template class QUBFAST_API pointy_col_vector<char>;
QUBFAST_TEMPLATE template class QUBFAST_API pointy_col_vector<short>;
QUBFAST_TEMPLATE template class QUBFAST_API pointy_col_vector<int>;
QUBFAST_TEMPLATE template class QUBFAST_API pointy_col_vector<float>;
QUBFAST_TEMPLATE template class QUBFAST_API pointy_col_vector<double>;
#endif
#endif