From 6e39d531ed36d043e6f6fee6befca2be00fd3f57 Mon Sep 17 00:00:00 2001 From: ancarola Date: Sun, 30 Jun 2019 22:21:54 +0200 Subject: Optimized matrix section - Vector iterators: allow to iterate on rows, columns or diagonals - Transposition doesn't affect allocated space, O(1) --- include/mm/experiments/tranpositions.hpp | 284 +++++++++++++++++++++++++++++++ 1 file changed, 284 insertions(+) create mode 100644 include/mm/experiments/tranpositions.hpp (limited to 'include/mm/experiments/tranpositions.hpp') diff --git a/include/mm/experiments/tranpositions.hpp b/include/mm/experiments/tranpositions.hpp new file mode 100644 index 0000000..f124a5c --- /dev/null +++ b/include/mm/experiments/tranpositions.hpp @@ -0,0 +1,284 @@ +#pragma once + +template +class mm::access : virtual public mm::basic_matrix +{ +public: + template + friend class mm::access; + + using mm::basic_matrix::basic_matrix; + + access(mm::basic_matrix&& m) + : basic_matrix(m) {} + + virtual T& at(std::size_t row, std::size_t col) = 0; + virtual const T& at(std::size_t row, std::size_t col) const = 0; + + static constexpr std::size_t rows = Regular ? Rows : Cols; + static constexpr std::size_t cols = Regular ? Cols : Rows; +}; + +template +class mm::row_access : public mm::access +{ +public: + template + friend class mm::row_access; + + using mm::access::access; + + row_access(mm::basic_matrix&& m) + : access(m) {} + + virtual T& at(std::size_t row, std::size_t col) override; + virtual const T& at(std::size_t row, std::size_t col) const override; + + row_iterator operator[](std::size_t index); + const_row_iterator operator[](std::size_t index) const; +}; + +template +class mm::col_access : public mm::access +{ +public: + template + friend class mm::access; + + using mm::access::access; + + col_access(mm::basic_matrix&& m) + : access(m) {} + + virtual T& at(std::size_t row, std::size_t col) override; + virtual const T& at(std::size_t row, std::size_t col) const override; + + col_iterator operator[](std::size_t index); + const_col_iterator operator[](std::size_t index) const; +}; + +/* + * Square interface + */ + +template +class mm::square_interface : virtual public mm::basic_matrix +{ +public: + + template + friend class mm::square_interface; + + using mm::basic_matrix::basic_matrix; + + T trace(); + inline T tr() { return trace(); } + + mm::diag_iterator diagonal_iter(int index = 0) + { + return mm::diag_iterator(*this, index); + } + + mm::diag_iterator diagonal_iter(int index = 0) const + { + return mm::const_diag_iterator(*this, index); + } + + // TODO, determinant + + /// in place inverse + // TODO, det != 0 + // TODO, use gauss jordan for invertible ones + //void invert();, TODO, section algorithm +}; + +/* + * derivated classes + */ + +// simple format matrix +template +class mm::matrix : public mm::row_access +{ +public: + using mm::row_access::row_access; + + matrix(mm::t_matrix&& m) + : row_access(std::move>(m)) + { + + } + + operator mm::t_matrix() + { + return mm::t_matrix(*this); + } + + mm::t_matrix& t() + { + return static_cast>(*this); + } + + const mm::t_matrix& t() const + { + return static_cast>(*this); + } +}; + +template +class mm::t_matrix : public mm::col_access +{ +public: + using mm::col_access::col_access; + + t_matrix(mm::matrix&& m) + : col_access(std::move>(m)) + { + + } + + operator mm::matrix() + { + return mm::matrix(*this); + } + + mm::matrix& t() + { + return static_cast>(*this); + } + + const mm::matrix& t() const + { + return static_cast>(*this); + } +}; + +// transposed matrix +/*template +class mm::t_matrix : public mm::basic_matrix, virtual public mm::access +{ +public: + using mm::basic_matrix::basic_matrix; +};*/ + +/* row vector specialization */ +template +class mm::row_vec : public mm::matrix { +public: + using mm::matrix::matrix; + + // TODO, begin, end +}; + +/* column vector specialization */ +template +class mm::col_vec : public mm::matrix { +public: + using mm::matrix::matrix; + + // TODO, begin, end +}; + +/* square matrix specialization */ +template +class mm::square_matrix : public mm::matrix, public mm::square_interface { +public: + using mm::matrix::matrix; + + // get the identity of size N + static inline constexpr square_matrix identity() { + mm::square_matrix i; + for (unsigned row = 0; row < N; row++) + for (unsigned col = 0; col < N; col++) + i.at(row, col) = (row == col) ? 1 : 0; + + return i; + } +}; + +template +class mm::t_square_matrix : public mm::t_matrix, public mm::square_interface { +public: + using mm::t_matrix::t_matrix; +}; + +/* + * K-diagonal square matrix format + * K is bounded between ]-N, N[ + */ + +/*template +class mm::diagonal_matrix : public mm::square_matrix +{ +public: + using mm::square_matrix::square_matrix; + + // TODO, redefine at, operator[] + // TODO, matrix multiplication +};*/ + +/* + * Accessors implementation + */ + +template +T& mm::row_access::at(std::size_t row, std::size_t col) +{ + return mm::basic_matrix::data[row * Cols + col]; +} + +template +const T& mm::row_access::at(std::size_t row, std::size_t col) const +{ + return mm::basic_matrix::data[row * Cols + col]; +} + +template +T& mm::col_access::at(std::size_t row, std::size_t col) +{ + return mm::basic_matrix::data[col * Cols + row]; // transpose +} + +template +const T& mm::col_access::at(std::size_t row, std::size_t col) const +{ + return mm::basic_matrix::data[col * Cols + row]; // transpose +} + +template +mm::row_iterator mm::row_access::operator[](std::size_t index) +{ + return mm::row_iterator(*this, static_cast(index)); +} + +template +mm::const_row_iterator mm::row_access::operator[](std::size_t index) const +{ + return mm::const_row_iterator(*this, static_cast(index)); +} + +template +mm::col_iterator mm::col_access::operator[](std::size_t index) +{ + return mm::col_iterator(*this, static_cast(index)); +} + +template +mm::const_col_iterator mm::col_access::operator[](std::size_t index) const +{ + return mm::const_col_iterator(*this, static_cast(index)); +} + +/* Square interface implementation */ + +template +T mm::square_interface::trace() +{ + T sum = 0; + for (const auto& x : diagonal_iter()) + sum += x; + + return sum; +} + + -- cgit v1.2.1