1 #ifndef PURIFY_MAPPING_OPERATOR_H
2 #define PURIFY_MAPPING_OPERATOR_H
4 #include "purify/config.h"
10 template <
class STORAGE_INDEX_TYPE = t_
int>
13 IndexMapping(
const std::vector<STORAGE_INDEX_TYPE> &indices,
const STORAGE_INDEX_TYPE N,
14 const STORAGE_INDEX_TYPE start = 0)
15 : indices(indices), N(N), start(start){};
17 IndexMapping(
const ITER &first,
const ITER &end,
const STORAGE_INDEX_TYPE N,
18 const STORAGE_INDEX_TYPE start = 0)
19 :
IndexMapping(std::vector<STORAGE_INDEX_TYPE>(first, end), N, start) {}
20 IndexMapping(
const std::set<STORAGE_INDEX_TYPE> &indices,
const STORAGE_INDEX_TYPE N,
21 const STORAGE_INDEX_TYPE start = 0)
22 :
IndexMapping(indices.begin(), indices.end(), N, start) {}
25 template <
class T0,
class T1>
26 void operator()(Eigen::MatrixBase<T0>
const &input, Eigen::MatrixBase<T1>
const &output)
const {
27 auto &derived = output.const_cast_derived();
28 derived.resize(indices.size());
29 typename T0::Index i(0);
30 for (
auto const &index : indices) {
31 assert(index >= start and index < (N + start));
32 assert(derived.size() > i);
33 derived(i++) = input(index - start);
38 template <
class T0,
class T1>
39 void adjoint(Eigen::MatrixBase<T0>
const &input, Eigen::MatrixBase<T1>
const &output)
const {
40 assert(
static_cast<size_t>(input.size()) == indices.size());
41 auto &derived = output.const_cast_derived();
42 derived = T1::Zero(N, 1);
43 typename T0::Index i(0);
44 for (STORAGE_INDEX_TYPE
const &index : indices) {
45 assert(index >= start and index < (N + start));
46 derived(index - start) += input(i++);
50 t_int
rows()
const {
return indices.size(); }
51 STORAGE_INDEX_TYPE
cols()
const {
return N; }
54 std::vector<STORAGE_INDEX_TYPE> indices;
55 STORAGE_INDEX_TYPE start;
60 template <
class T0,
class STORAGE_INDEX_TYPE = t_
int>
61 std::set<STORAGE_INDEX_TYPE>
non_empty_outers(Eigen::SparseMatrixBase<T0>
const &matrix) {
62 std::set<STORAGE_INDEX_TYPE> result;
63 for (
typename T0::Index k = 0; k < matrix.derived().outerSize(); ++k)
64 for (
typename T0::InnerIterator it(matrix.derived(), k); it; ++it)
65 result.insert(
static_cast<STORAGE_INDEX_TYPE
>(it.col()));
72 static_assert(T0::IsRowMajor,
"Not tested for col major");
76 mapping.reserve(indices.size());
78 for (
auto const &index : indices) mapping.coeffRef(index) = i++;
80 std::vector<typename Sparse<typename T0::Scalar>::Index> rows(matrix.rows() + 1, 0);
81 std::vector<typename Sparse<typename T0::Scalar>::Index> cols(matrix.nonZeros(), 0);
82 rows[matrix.rows()] = matrix.nonZeros();
84 for (
typename T0::Index k = 0; k < matrix.outerSize(); ++k) {
86 for (
typename T0::InnerIterator it(matrix, k); it; ++it) {
87 cols[index] = mapping.coeff(it.col());
91 return Eigen::MappedSparseMatrix<
typename T0::Scalar, Eigen::RowMajor,
93 matrix.rows(), indices.size(), matrix.nonZeros(), rows.data(), cols.data(),
94 const_cast<typename T0::Scalar *
>(matrix.derived().valuePtr()));
IndexMapping(const ITER &first, const ITER &end, const STORAGE_INDEX_TYPE N, const STORAGE_INDEX_TYPE start=0)
IndexMapping(const std::vector< STORAGE_INDEX_TYPE > &indices, const STORAGE_INDEX_TYPE N, const STORAGE_INDEX_TYPE start=0)
IndexMapping(const std::set< STORAGE_INDEX_TYPE > &indices, const STORAGE_INDEX_TYPE N, const STORAGE_INDEX_TYPE start=0)
void adjoint(Eigen::MatrixBase< T0 > const &input, Eigen::MatrixBase< T1 > const &output) const
Vector of size N where non-zero elements are chosen from input at given indices.
STORAGE_INDEX_TYPE cols() const
void operator()(Eigen::MatrixBase< T0 > const &input, Eigen::MatrixBase< T1 > const &output) const
Creates a vector of elements equal to re-indexed inpu.
Eigen::SparseVector< T, Eigen::RowMajor, I > SparseVector
std::set< STORAGE_INDEX_TYPE > non_empty_outers(Eigen::SparseMatrixBase< T0 > const &matrix)
Indices of non empty outer indices.
Eigen::SparseMatrix< T, Eigen::RowMajor, I > Sparse
A matrix of a given type.
Sparse< typename T0::Scalar > compress_outer(T0 const &matrix)
Indices of non empty outer indices.