📄 matrix_sparse.hpp
字号:
BOOST_UBLAS_INLINE void reserve (size_type non_zeros, bool preserve = true) { detail::map_reserve (data (), restrict_nz (non_zeros)); } // Proxy support#ifdef BOOST_UBLAS_STRICT_MATRIX_SPARSE BOOST_UBLAS_INLINE pointer find_element (size_type i, size_type j) { iterator_type it (data ().find (functor_type::element (i, size1_, j, size2_))); if (it == data ().end () || (*it).first != functor_type::element (i, size1_, j, size2_)) return 0; return &(*it).second; }#endif // Element access BOOST_UBLAS_INLINE const_reference at_element (size_type i, size_type j) const { const_iterator_type it (data ().find (functor_type::element (i, size1_, j, size2_))); if (it == data ().end () || (*it).first != functor_type::element (i, size1_, j, size2_)) return zero_; return (*it).second; } BOOST_UBLAS_INLINE true_reference at_element (size_type i, size_type j) { return data () [functor_type::element (i, size1_, j, size2_)]; } BOOST_UBLAS_INLINE const_reference operator () (size_type i, size_type j) const { return at_element (i, j); } BOOST_UBLAS_INLINE reference operator () (size_type i, size_type j) {#ifndef BOOST_UBLAS_STRICT_MATRIX_SPARSE return at_element (i, j);#else return reference (*this, i, j);#endif } // Assignment BOOST_UBLAS_INLINE sparse_matrix &operator = (const sparse_matrix &m) { if (this != &m) { size1_ = m.size1_; size2_ = m.size2_; data () = m.data (); } return *this; } BOOST_UBLAS_INLINE sparse_matrix &assign_temporary (sparse_matrix &m) { swap (m); return *this; } template<class AE> BOOST_UBLAS_INLINE sparse_matrix &operator = (const matrix_expression<AE> &ae) { self_type temporary (ae, detail::map_capacity (data ())); return assign_temporary (temporary); } template<class AE> BOOST_UBLAS_INLINE sparse_matrix &assign (const matrix_expression<AE> &ae) { matrix_assign (scalar_assign<true_reference, BOOST_UBLAS_TYPENAME AE::value_type> (), *this, ae); return *this; } template<class AE> BOOST_UBLAS_INLINE sparse_matrix& operator += (const matrix_expression<AE> &ae) { self_type temporary (*this + ae, detail::map_capacity (data ())); return assign_temporary (temporary); } template<class AE> BOOST_UBLAS_INLINE sparse_matrix &plus_assign (const matrix_expression<AE> &ae) { matrix_assign (scalar_plus_assign<true_reference, BOOST_UBLAS_TYPENAME AE::value_type> (), *this, ae); return *this; } template<class AE> BOOST_UBLAS_INLINE sparse_matrix& operator -= (const matrix_expression<AE> &ae) { self_type temporary (*this - ae, detail::map_capacity (data ())); return assign_temporary (temporary); } template<class AE> BOOST_UBLAS_INLINE sparse_matrix &minus_assign (const matrix_expression<AE> &ae) { matrix_assign (scalar_minus_assign<true_reference, BOOST_UBLAS_TYPENAME AE::value_type> (), *this, ae); return *this; } template<class AT> BOOST_UBLAS_INLINE sparse_matrix& operator *= (const AT &at) { matrix_assign_scalar (scalar_multiplies_assign<true_reference, AT> (), *this, at); return *this; } template<class AT> BOOST_UBLAS_INLINE sparse_matrix& operator /= (const AT &at) { matrix_assign_scalar (scalar_divides_assign<true_reference, AT> (), *this, at); return *this; } // Swapping BOOST_UBLAS_INLINE void swap (sparse_matrix &m) { if (this != &m) { std::swap (size1_, m.size1_); std::swap (size2_, m.size2_); data ().swap (m.data ()); } }#ifndef BOOST_UBLAS_NO_MEMBER_FRIENDS BOOST_UBLAS_INLINE friend void swap (sparse_matrix &m1, sparse_matrix &m2) { m1.swap (m2); }#endif // Element insertion and erasure BOOST_UBLAS_INLINE void insert (size_type i, size_type j, const_reference t) { BOOST_UBLAS_CHECK (data ().find (functor_type::element (i, size1_, j, size2_)) == data ().end (), bad_index ()); data ().insert (data ().end (), BOOST_UBLAS_TYPENAME array_type::value_type (functor_type::element (i, size1_, j, size2_), t)); } BOOST_UBLAS_INLINE void erase (size_type i, size_type j) { // FIXME: shouldn't we use const_iterator_type here? iterator_type it = data ().find (functor_type::element (i, size1_, j, size2_)); if (it == data ().end ()) return; data ().erase (it); } BOOST_UBLAS_INLINE void clear () { data ().clear (); } // Iterator types private: // Use storage iterator typedef typename A::const_iterator const_iterator_type; typedef typename A::iterator iterator_type; public: class const_iterator1; class iterator1; class const_iterator2; class iterator2;#ifdef BOOST_MSVC_STD_ITERATOR typedef reverse_iterator_base1<const_iterator1, value_type, const_reference> const_reverse_iterator1; typedef reverse_iterator_base1<iterator1, value_type, reference> reverse_iterator1; typedef reverse_iterator_base2<const_iterator2, value_type, const_reference> const_reverse_iterator2; typedef reverse_iterator_base2<iterator2, value_type, reference> reverse_iterator2;#else typedef reverse_iterator_base1<const_iterator1> const_reverse_iterator1; typedef reverse_iterator_base1<iterator1> reverse_iterator1; typedef reverse_iterator_base2<const_iterator2> const_reverse_iterator2; typedef reverse_iterator_base2<iterator2> reverse_iterator2;#endif // Element lookup // This function seems to be big. So we do not let the compiler inline it. // BOOST_UBLAS_INLINE const_iterator1 find1 (int rank, size_type i, size_type j, int direction = 1) const { const_iterator_type it (data ().lower_bound (functor_type::address (i, size1_, j, size2_))); const_iterator_type it_end (data ().end ()); size_type index1 = size_type (-1); size_type index2 = size_type (-1); while (rank == 1 && it != it_end) { index1 = functor_type::index1 ((*it).first, size1_, size2_); index2 = functor_type::index2 ((*it).first, size1_, size2_); if (direction > 0) { if ((index1 >= i && index2 == j) || (i >= size1_)) break; ++ i; } else /* if (direction < 0) */ { if ((index1 <= i && index2 == j) || (i == 0)) break; -- i; } it = data ().lower_bound (functor_type::address (i, size1_, j, size2_)); } if (rank == 1 && index2 != j) { if (direction > 0) i = size1_; else /* if (direction < 0) */ i = 0; rank = 0; } return const_iterator1 (*this, rank, i, j, it); } // This function seems to be big. So we do not let the compiler inline it. // BOOST_UBLAS_INLINE iterator1 find1 (int rank, size_type i, size_type j, int direction = 1) { iterator_type it (data ().lower_bound (functor_type::address (i, size1_, j, size2_))); iterator_type it_end (data ().end ()); size_type index1 = size_type (-1); size_type index2 = size_type (-1); while (rank == 1 && it != it_end) { index1 = functor_type::index1 ((*it).first, size1_, size2_); index2 = functor_type::index2 ((*it).first, size1_, size2_); if (direction > 0) { if ((index1 >= i && index2 == j) || (i >= size1_)) break; ++ i; } else /* if (direction < 0) */ { if ((index1 <= i && index2 == j) || (i == 0)) break; -- i; } it = data ().lower_bound (functor_type::address (i, size1_, j, size2_)); } if (rank == 1 && index2 != j) { if (direction > 0) i = size1_; else /* if (direction < 0) */ i = 0; rank = 0; } return iterator1 (*this, rank, i, j, it); } // This function seems to be big. So we do not let the compiler inline it. // BOOST_UBLAS_INLINE const_iterator2 find2 (int rank, size_type i, size_type j, int direction = 1) const { const_iterator_type it (data ().lower_bound (functor_type::address (i, size1_, j, size2_))); const_iterator_type it_end (data ().end ()); size_type index1 = size_type (-1); size_type index2 = size_type (-1); while (rank == 1 && it != it_end) { index1 = functor_type::index1 ((*it).first, size1_, size2_); index2 = functor_type::index2 ((*it).first, size1_, size2_); if (direction > 0) { if ((index2 >= j && index1 == i) || (j >= size2_)) break; ++ j; } else /* if (direction < 0) */ { if ((index2 <= j && index1 == i) || (j == 0)) break; -- j; } it = data ().lower_bound (functor_type::address (i, size1_, j, size2_)); } if (rank == 1 && index1 != i) { if (direction > 0) j = size2_; else /* if (direction < 0) */ j = 0; rank = 0; } return const_iterator2 (*this, rank, i, j, it); } // This function seems to be big. So we do not let the compiler inline it. // BOOST_UBLAS_INLINE iterator2 find2 (int rank, size_type i, size_type j, int direction = 1) { iterator_type it (data ().lower_bound (functor_type::address (i, size1_, j, size2_))); iterator_type it_end (data ().end ()); size_type index1 = size_type (-1); size_type index2 = size_type (-1); while (rank == 1 && it != it_end) { index1 = functor_type::index1 ((*it).first, size1_, size2_); index2 = functor_type::index2 ((*it).first, size1_, size2_); if (direction > 0) { if ((index2 >= j && index1 == i) || (j >= size2_)) break; ++ j; } else /* if (direction < 0) */ { if ((index2 <= j && index1 == i) || (j == 0)) break; -- j; } it = data ().lower_bound (functor_type::address (i, size1_, j, size2_)); } if (rank == 1 && index1 != i) { if (direction > 0) j = size2_; else /* if (direction < 0) */ j = 0; rank = 0; } return iterator2 (*this, rank, i, j, it); } class const_iterator1: public container_const_reference<sparse_matrix>, public bidirectional_iterator_base<sparse_bidirectional_iterator_tag, const_iterator1, value_type> { public: typedef sparse_bidirectional_iterator_tag iterator_category;#ifdef BOOST_MSVC_STD_ITERATOR typedef const_reference reference;#else typedef typename sparse_matrix::value_type value_type; typedef typename sparse_matrix::difference_type difference_type; typedef typename sparse_matrix::const_reference reference; typedef const typename sparse_matrix::pointer pointer;#endif typedef const_iterator2 dual_iterator_type; typedef const_reverse_iterator2 dual_reverse_iterator_type; // Construction and destruction BOOST_UBLAS_INLINE const_iterator1 (): container_const_reference<self_type> (), rank_ (), i_ (), j_ (), it_ () {} BOOST_UBLAS_INLINE const_iterator1 (const self_type &m, int rank, size_type i, size_type j, const const_iterator_type &it): container_const_reference<self_type> (m), rank_ (rank), i_ (i), j_ (j), it_ (it) {} BOOST_UBLAS_INLINE const_iterator1 (const iterator1 &it): container_const_reference<self_type> (it ()), rank_ (it.rank_), i_ (it.i_), j_ (it.j_), it_ (it.it_) {} // Arithmetic BOOST_UBLAS_INLINE const_iterator1 &operator ++ () { if (rank_ == 1 && functor_type::fast1 ()) ++ it_; else *this = (*this) ().find1 (rank_, index1 () + 1, j_, 1); return *this; } BOOST_UBLAS_INLINE const_iterator1 &operator -- () { if (rank_ == 1 && functor_type::fast1 ()) -- it_; else *this = (*this) ().find1 (rank_, index1 () - 1, j_, -1); return *this;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -