1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/os/ossrv/ossrv_pub/boost_apis/boost/numeric/ublas/symmetric.hpp Fri Jun 15 03:10:57 2012 +0200
1.3 @@ -0,0 +1,2133 @@
1.4 +//
1.5 +// Copyright (c) 2000-2002
1.6 +// Joerg Walter, Mathias Koch
1.7 +//
1.8 +// Permission to use, copy, modify, distribute and sell this software
1.9 +// and its documentation for any purpose is hereby granted without fee,
1.10 +// provided that the above copyright notice appear in all copies and
1.11 +// that both that copyright notice and this permission notice appear
1.12 +// in supporting documentation. The authors make no representations
1.13 +// about the suitability of this software for any purpose.
1.14 +// It is provided "as is" without express or implied warranty.
1.15 +//
1.16 +// The authors gratefully acknowledge the support of
1.17 +// GeNeSys mbH & Co. KG in producing this work.
1.18 +//
1.19 +
1.20 +#ifndef _BOOST_UBLAS_SYMMETRIC_
1.21 +#define _BOOST_UBLAS_SYMMETRIC_
1.22 +
1.23 +#include <boost/numeric/ublas/matrix.hpp>
1.24 +#include <boost/numeric/ublas/detail/temporary.hpp>
1.25 +
1.26 +// Iterators based on ideas of Jeremy Siek
1.27 +// Symmetric matrices are square. Thanks to Peter Schmitteckert for spotting this.
1.28 +
1.29 +namespace boost { namespace numeric { namespace ublas {
1.30 +
1.31 + template<class M>
1.32 + bool is_symmetric (const M &m) {
1.33 + typedef typename M::size_type size_type;
1.34 +
1.35 + if (m.size1 () != m.size2 ())
1.36 + return false;
1.37 + size_type size = BOOST_UBLAS_SAME (m.size1 (), m.size2 ());
1.38 + for (size_type i = 0; i < size; ++ i) {
1.39 + for (size_type j = i; j < size; ++ j) {
1.40 + if (m (i, j) != m (j, i))
1.41 + return false;
1.42 + }
1.43 + }
1.44 + return true;
1.45 + }
1.46 +
1.47 + // Array based symmetric matrix class
1.48 + template<class T, class TRI, class L, class A>
1.49 + class symmetric_matrix:
1.50 + public matrix_container<symmetric_matrix<T, TRI, L, A> > {
1.51 +
1.52 + typedef T *pointer;
1.53 + typedef TRI triangular_type;
1.54 + typedef L layout_type;
1.55 + typedef symmetric_matrix<T, TRI, L, A> self_type;
1.56 + public:
1.57 +#ifdef BOOST_UBLAS_ENABLE_PROXY_SHORTCUTS
1.58 + using matrix_container<self_type>::operator ();
1.59 +#endif
1.60 + typedef typename A::size_type size_type;
1.61 + typedef typename A::difference_type difference_type;
1.62 + typedef T value_type;
1.63 + typedef const T &const_reference;
1.64 + typedef T &reference;
1.65 + typedef A array_type;
1.66 +
1.67 + typedef const matrix_reference<const self_type> const_closure_type;
1.68 + typedef matrix_reference<self_type> closure_type;
1.69 + typedef vector<T, A> vector_temporary_type;
1.70 + typedef matrix<T, L, A> matrix_temporary_type; // general sub-matrix
1.71 + typedef packed_tag storage_category;
1.72 + typedef typename L::orientation_category orientation_category;
1.73 +
1.74 + // Construction and destruction
1.75 + BOOST_UBLAS_INLINE
1.76 + symmetric_matrix ():
1.77 + matrix_container<self_type> (),
1.78 + size_ (0), data_ (0) {}
1.79 + BOOST_UBLAS_INLINE
1.80 + symmetric_matrix (size_type size):
1.81 + matrix_container<self_type> (),
1.82 + size_ (BOOST_UBLAS_SAME (size, size)), data_ (triangular_type::packed_size (layout_type (), size, size)) {
1.83 + }
1.84 + BOOST_UBLAS_INLINE
1.85 + symmetric_matrix (size_type size1, size_type size2):
1.86 + matrix_container<self_type> (),
1.87 + size_ (BOOST_UBLAS_SAME (size1, size2)), data_ (triangular_type::packed_size (layout_type (), size1, size2)) {
1.88 + }
1.89 + BOOST_UBLAS_INLINE
1.90 + symmetric_matrix (size_type size, const array_type &data):
1.91 + matrix_container<self_type> (),
1.92 + size_ (size), data_ (data) {}
1.93 + BOOST_UBLAS_INLINE
1.94 + symmetric_matrix (const symmetric_matrix &m):
1.95 + matrix_container<self_type> (),
1.96 + size_ (m.size_), data_ (m.data_) {}
1.97 + template<class AE>
1.98 + BOOST_UBLAS_INLINE
1.99 + symmetric_matrix (const matrix_expression<AE> &ae):
1.100 + matrix_container<self_type> (),
1.101 + size_ (BOOST_UBLAS_SAME (ae ().size1 (), ae ().size2 ())),
1.102 + data_ (triangular_type::packed_size (layout_type (), size_, size_)) {
1.103 + matrix_assign<scalar_assign> (*this, ae);
1.104 + }
1.105 +
1.106 + // Accessors
1.107 + BOOST_UBLAS_INLINE
1.108 + size_type size1 () const {
1.109 + return size_;
1.110 + }
1.111 + BOOST_UBLAS_INLINE
1.112 + size_type size2 () const {
1.113 + return size_;
1.114 + }
1.115 +
1.116 + // Storage accessors
1.117 + BOOST_UBLAS_INLINE
1.118 + const array_type &data () const {
1.119 + return data_;
1.120 + }
1.121 + BOOST_UBLAS_INLINE
1.122 + array_type &data () {
1.123 + return data_;
1.124 + }
1.125 +
1.126 + // Resizing
1.127 + BOOST_UBLAS_INLINE
1.128 + void resize (size_type size, bool preserve = true) {
1.129 + if (preserve) {
1.130 + self_type temporary (size, size);
1.131 + detail::matrix_resize_preserve<layout_type> (*this, temporary);
1.132 + }
1.133 + else {
1.134 + data ().resize (triangular_type::packed_size (layout_type (), size, size));
1.135 + size_ = size;
1.136 + }
1.137 + }
1.138 + BOOST_UBLAS_INLINE
1.139 + void resize (size_type size1, size_type size2, bool preserve = true) {
1.140 + resize (BOOST_UBLAS_SAME (size1, size2), preserve);
1.141 + }
1.142 + BOOST_UBLAS_INLINE
1.143 + void resize_packed_preserve (size_type size) {
1.144 + size_ = BOOST_UBLAS_SAME (size, size);
1.145 + data ().resize (triangular_type::packed_size (layout_type (), size_, size_), value_type ());
1.146 + }
1.147 +
1.148 + // Element access
1.149 + BOOST_UBLAS_INLINE
1.150 + const_reference operator () (size_type i, size_type j) const {
1.151 + BOOST_UBLAS_CHECK (i < size_, bad_index ());
1.152 + BOOST_UBLAS_CHECK (j < size_, bad_index ());
1.153 + if (triangular_type::other (i, j))
1.154 + return data () [triangular_type::element (layout_type (), i, size_, j, size_)];
1.155 + else
1.156 + return data () [triangular_type::element (layout_type (), j, size_, i, size_)];
1.157 + }
1.158 + BOOST_UBLAS_INLINE
1.159 + reference at_element (size_type i, size_type j) {
1.160 + BOOST_UBLAS_CHECK (i < size_, bad_index ());
1.161 + BOOST_UBLAS_CHECK (j < size_, bad_index ());
1.162 + return data () [triangular_type::element (layout_type (), i, size_, j, size_)];
1.163 + }
1.164 + BOOST_UBLAS_INLINE
1.165 + reference operator () (size_type i, size_type j) {
1.166 + BOOST_UBLAS_CHECK (i < size_, bad_index ());
1.167 + BOOST_UBLAS_CHECK (j < size_, bad_index ());
1.168 + if (triangular_type::other (i, j))
1.169 + return data () [triangular_type::element (layout_type (), i, size_, j, size_)];
1.170 + else
1.171 + return data () [triangular_type::element (layout_type (), j, size_, i, size_)];
1.172 + }
1.173 +
1.174 + // Element assignment
1.175 + BOOST_UBLAS_INLINE
1.176 + reference insert_element (size_type i, size_type j, const_reference t) {
1.177 + return (operator () (i, j) = t);
1.178 + }
1.179 + BOOST_UBLAS_INLINE
1.180 + void erase_element (size_type i, size_type j) {
1.181 + operator () (i, j) = value_type/*zero*/();
1.182 + }
1.183 +
1.184 + // Zeroing
1.185 + BOOST_UBLAS_INLINE
1.186 + void clear () {
1.187 + // data ().clear ();
1.188 + std::fill (data ().begin (), data ().end (), value_type/*zero*/());
1.189 + }
1.190 +
1.191 + // Assignment
1.192 + BOOST_UBLAS_INLINE
1.193 + symmetric_matrix &operator = (const symmetric_matrix &m) {
1.194 + size_ = m.size_;
1.195 + data () = m.data ();
1.196 + return *this;
1.197 + }
1.198 + BOOST_UBLAS_INLINE
1.199 + symmetric_matrix &assign_temporary (symmetric_matrix &m) {
1.200 + swap (m);
1.201 + return *this;
1.202 + }
1.203 + template<class AE>
1.204 + BOOST_UBLAS_INLINE
1.205 + symmetric_matrix &operator = (const matrix_expression<AE> &ae) {
1.206 + self_type temporary (ae);
1.207 + return assign_temporary (temporary);
1.208 + }
1.209 + template<class AE>
1.210 + BOOST_UBLAS_INLINE
1.211 + symmetric_matrix &assign (const matrix_expression<AE> &ae) {
1.212 + matrix_assign<scalar_assign> (*this, ae);
1.213 + return *this;
1.214 + }
1.215 + template<class AE>
1.216 + BOOST_UBLAS_INLINE
1.217 + symmetric_matrix& operator += (const matrix_expression<AE> &ae) {
1.218 + self_type temporary (*this + ae);
1.219 + return assign_temporary (temporary);
1.220 + }
1.221 + template<class AE>
1.222 + BOOST_UBLAS_INLINE
1.223 + symmetric_matrix &plus_assign (const matrix_expression<AE> &ae) {
1.224 + matrix_assign<scalar_plus_assign> (*this, ae);
1.225 + return *this;
1.226 + }
1.227 + template<class AE>
1.228 + BOOST_UBLAS_INLINE
1.229 + symmetric_matrix& operator -= (const matrix_expression<AE> &ae) {
1.230 + self_type temporary (*this - ae);
1.231 + return assign_temporary (temporary);
1.232 + }
1.233 + template<class AE>
1.234 + BOOST_UBLAS_INLINE
1.235 + symmetric_matrix &minus_assign (const matrix_expression<AE> &ae) {
1.236 + matrix_assign<scalar_minus_assign> (*this, ae);
1.237 + return *this;
1.238 + }
1.239 + template<class AT>
1.240 + BOOST_UBLAS_INLINE
1.241 + symmetric_matrix& operator *= (const AT &at) {
1.242 + matrix_assign_scalar<scalar_multiplies_assign> (*this, at);
1.243 + return *this;
1.244 + }
1.245 + template<class AT>
1.246 + BOOST_UBLAS_INLINE
1.247 + symmetric_matrix& operator /= (const AT &at) {
1.248 + matrix_assign_scalar<scalar_divides_assign> (*this, at);
1.249 + return *this;
1.250 + }
1.251 +
1.252 + // Swapping
1.253 + BOOST_UBLAS_INLINE
1.254 + void swap (symmetric_matrix &m) {
1.255 + if (this != &m) {
1.256 + std::swap (size_, m.size_);
1.257 + data ().swap (m.data ());
1.258 + }
1.259 + }
1.260 + BOOST_UBLAS_INLINE
1.261 + friend void swap (symmetric_matrix &m1, symmetric_matrix &m2) {
1.262 + m1.swap (m2);
1.263 + }
1.264 +
1.265 + // Iterator types
1.266 +#ifdef BOOST_UBLAS_USE_INDEXED_ITERATOR
1.267 + typedef indexed_iterator1<self_type, packed_random_access_iterator_tag> iterator1;
1.268 + typedef indexed_iterator2<self_type, packed_random_access_iterator_tag> iterator2;
1.269 + typedef indexed_const_iterator1<self_type, dense_random_access_iterator_tag> const_iterator1;
1.270 + typedef indexed_const_iterator2<self_type, dense_random_access_iterator_tag> const_iterator2;
1.271 +#else
1.272 + class const_iterator1;
1.273 + class iterator1;
1.274 + class const_iterator2;
1.275 + class iterator2;
1.276 +#endif
1.277 + typedef reverse_iterator_base1<const_iterator1> const_reverse_iterator1;
1.278 + typedef reverse_iterator_base1<iterator1> reverse_iterator1;
1.279 + typedef reverse_iterator_base2<const_iterator2> const_reverse_iterator2;
1.280 + typedef reverse_iterator_base2<iterator2> reverse_iterator2;
1.281 +
1.282 + // Element lookup
1.283 + BOOST_UBLAS_INLINE
1.284 + const_iterator1 find1 (int /* rank */, size_type i, size_type j) const {
1.285 + return const_iterator1 (*this, i, j);
1.286 + }
1.287 + BOOST_UBLAS_INLINE
1.288 + iterator1 find1 (int rank, size_type i, size_type j) {
1.289 + if (rank == 1)
1.290 + i = triangular_type::mutable_restrict1 (i, j);
1.291 + return iterator1 (*this, i, j);
1.292 + }
1.293 + BOOST_UBLAS_INLINE
1.294 + const_iterator2 find2 (int /* rank */, size_type i, size_type j) const {
1.295 + return const_iterator2 (*this, i, j);
1.296 + }
1.297 + BOOST_UBLAS_INLINE
1.298 + iterator2 find2 (int rank, size_type i, size_type j) {
1.299 + if (rank == 1)
1.300 + j = triangular_type::mutable_restrict2 (i, j);
1.301 + return iterator2 (*this, i, j);
1.302 + }
1.303 +
1.304 + // Iterators simply are indices.
1.305 +
1.306 +#ifndef BOOST_UBLAS_USE_INDEXED_ITERATOR
1.307 + class const_iterator1:
1.308 + public container_const_reference<symmetric_matrix>,
1.309 + public random_access_iterator_base<dense_random_access_iterator_tag,
1.310 + const_iterator1, value_type> {
1.311 + public:
1.312 + typedef typename symmetric_matrix::value_type value_type;
1.313 + typedef typename symmetric_matrix::difference_type difference_type;
1.314 + typedef typename symmetric_matrix::const_reference reference;
1.315 + typedef const typename symmetric_matrix::pointer pointer;
1.316 +
1.317 + typedef const_iterator2 dual_iterator_type;
1.318 + typedef const_reverse_iterator2 dual_reverse_iterator_type;
1.319 +
1.320 + // Construction and destruction
1.321 + BOOST_UBLAS_INLINE
1.322 + const_iterator1 ():
1.323 + container_const_reference<self_type> (), it1_ (), it2_ () {}
1.324 + BOOST_UBLAS_INLINE
1.325 + const_iterator1 (const self_type &m, size_type it1, size_type it2):
1.326 + container_const_reference<self_type> (m), it1_ (it1), it2_ (it2) {}
1.327 + BOOST_UBLAS_INLINE
1.328 + const_iterator1 (const iterator1 &it):
1.329 + container_const_reference<self_type> (it ()), it1_ (it.it1_), it2_ (it.it2_) {}
1.330 +
1.331 + // Arithmetic
1.332 + BOOST_UBLAS_INLINE
1.333 + const_iterator1 &operator ++ () {
1.334 + ++ it1_;
1.335 + return *this;
1.336 + }
1.337 + BOOST_UBLAS_INLINE
1.338 + const_iterator1 &operator -- () {
1.339 + -- it1_;
1.340 + return *this;
1.341 + }
1.342 + BOOST_UBLAS_INLINE
1.343 + const_iterator1 &operator += (difference_type n) {
1.344 + it1_ += n;
1.345 + return *this;
1.346 + }
1.347 + BOOST_UBLAS_INLINE
1.348 + const_iterator1 &operator -= (difference_type n) {
1.349 + it1_ -= n;
1.350 + return *this;
1.351 + }
1.352 + BOOST_UBLAS_INLINE
1.353 + difference_type operator - (const const_iterator1 &it) const {
1.354 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.355 + BOOST_UBLAS_CHECK (it2_ == it.it2_, external_logic ());
1.356 + return it1_ - it.it1_;
1.357 + }
1.358 +
1.359 + // Dereference
1.360 + BOOST_UBLAS_INLINE
1.361 + const_reference operator * () const {
1.362 + return (*this) () (it1_, it2_);
1.363 + }
1.364 + BOOST_UBLAS_INLINE
1.365 + const_reference operator [] (difference_type n) const {
1.366 + return *(*this + n);
1.367 + }
1.368 +
1.369 +#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
1.370 + BOOST_UBLAS_INLINE
1.371 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.372 + typename self_type::
1.373 +#endif
1.374 + const_iterator2 begin () const {
1.375 + return (*this) ().find2 (1, it1_, 0);
1.376 + }
1.377 + BOOST_UBLAS_INLINE
1.378 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.379 + typename self_type::
1.380 +#endif
1.381 + const_iterator2 end () const {
1.382 + return (*this) ().find2 (1, it1_, (*this) ().size2 ());
1.383 + }
1.384 + BOOST_UBLAS_INLINE
1.385 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.386 + typename self_type::
1.387 +#endif
1.388 + const_reverse_iterator2 rbegin () const {
1.389 + return const_reverse_iterator2 (end ());
1.390 + }
1.391 + BOOST_UBLAS_INLINE
1.392 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.393 + typename self_type::
1.394 +#endif
1.395 + const_reverse_iterator2 rend () const {
1.396 + return const_reverse_iterator2 (begin ());
1.397 + }
1.398 +#endif
1.399 +
1.400 + // Indices
1.401 + BOOST_UBLAS_INLINE
1.402 + size_type index1 () const {
1.403 + return it1_;
1.404 + }
1.405 + BOOST_UBLAS_INLINE
1.406 + size_type index2 () const {
1.407 + return it2_;
1.408 + }
1.409 +
1.410 + // Assignment
1.411 + BOOST_UBLAS_INLINE
1.412 + const_iterator1 &operator = (const const_iterator1 &it) {
1.413 + container_const_reference<self_type>::assign (&it ());
1.414 + it1_ = it.it1_;
1.415 + it2_ = it.it2_;
1.416 + return *this;
1.417 + }
1.418 +
1.419 + // Comparison
1.420 + BOOST_UBLAS_INLINE
1.421 + bool operator == (const const_iterator1 &it) const {
1.422 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.423 + BOOST_UBLAS_CHECK (it2_ == it.it2_, external_logic ());
1.424 + return it1_ == it.it1_;
1.425 + }
1.426 + BOOST_UBLAS_INLINE
1.427 + bool operator < (const const_iterator1 &it) const {
1.428 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.429 + BOOST_UBLAS_CHECK (it2_ == it.it2_, external_logic ());
1.430 + return it1_ < it.it1_;
1.431 + }
1.432 +
1.433 + private:
1.434 + size_type it1_;
1.435 + size_type it2_;
1.436 + };
1.437 +#endif
1.438 +
1.439 + BOOST_UBLAS_INLINE
1.440 + const_iterator1 begin1 () const {
1.441 + return find1 (0, 0, 0);
1.442 + }
1.443 + BOOST_UBLAS_INLINE
1.444 + const_iterator1 end1 () const {
1.445 + return find1 (0, size_, 0);
1.446 + }
1.447 +
1.448 +#ifndef BOOST_UBLAS_USE_INDEXED_ITERATOR
1.449 + class iterator1:
1.450 + public container_reference<symmetric_matrix>,
1.451 + public random_access_iterator_base<packed_random_access_iterator_tag,
1.452 + iterator1, value_type> {
1.453 + public:
1.454 + typedef typename symmetric_matrix::value_type value_type;
1.455 + typedef typename symmetric_matrix::difference_type difference_type;
1.456 + typedef typename symmetric_matrix::reference reference;
1.457 + typedef typename symmetric_matrix::pointer pointer;
1.458 + typedef iterator2 dual_iterator_type;
1.459 + typedef reverse_iterator2 dual_reverse_iterator_type;
1.460 +
1.461 + // Construction and destruction
1.462 + BOOST_UBLAS_INLINE
1.463 + iterator1 ():
1.464 + container_reference<self_type> (), it1_ (), it2_ () {}
1.465 + BOOST_UBLAS_INLINE
1.466 + iterator1 (self_type &m, size_type it1, size_type it2):
1.467 + container_reference<self_type> (m), it1_ (it1), it2_ (it2) {}
1.468 +
1.469 + // Arithmetic
1.470 + BOOST_UBLAS_INLINE
1.471 + iterator1 &operator ++ () {
1.472 + ++ it1_;
1.473 + return *this;
1.474 + }
1.475 + BOOST_UBLAS_INLINE
1.476 + iterator1 &operator -- () {
1.477 + -- it1_;
1.478 + return *this;
1.479 + }
1.480 + BOOST_UBLAS_INLINE
1.481 + iterator1 &operator += (difference_type n) {
1.482 + it1_ += n;
1.483 + return *this;
1.484 + }
1.485 + BOOST_UBLAS_INLINE
1.486 + iterator1 &operator -= (difference_type n) {
1.487 + it1_ -= n;
1.488 + return *this;
1.489 + }
1.490 + BOOST_UBLAS_INLINE
1.491 + difference_type operator - (const iterator1 &it) const {
1.492 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.493 + BOOST_UBLAS_CHECK (it2_ == it.it2_, external_logic ());
1.494 + return it1_ - it.it1_;
1.495 + }
1.496 +
1.497 + // Dereference
1.498 + BOOST_UBLAS_INLINE
1.499 + reference operator * () const {
1.500 + return (*this) () (it1_, it2_);
1.501 + }
1.502 + BOOST_UBLAS_INLINE
1.503 + reference operator [] (difference_type n) const {
1.504 + return *(*this + n);
1.505 + }
1.506 +
1.507 +#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
1.508 + BOOST_UBLAS_INLINE
1.509 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.510 + typename self_type::
1.511 +#endif
1.512 + iterator2 begin () const {
1.513 + return (*this) ().find2 (1, it1_, 0);
1.514 + }
1.515 + BOOST_UBLAS_INLINE
1.516 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.517 + typename self_type::
1.518 +#endif
1.519 + iterator2 end () const {
1.520 + return (*this) ().find2 (1, it1_, (*this) ().size2 ());
1.521 + }
1.522 + BOOST_UBLAS_INLINE
1.523 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.524 + typename self_type::
1.525 +#endif
1.526 + reverse_iterator2 rbegin () const {
1.527 + return reverse_iterator2 (end ());
1.528 + }
1.529 + BOOST_UBLAS_INLINE
1.530 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.531 + typename self_type::
1.532 +#endif
1.533 + reverse_iterator2 rend () const {
1.534 + return reverse_iterator2 (begin ());
1.535 + }
1.536 +#endif
1.537 +
1.538 + // Indices
1.539 + BOOST_UBLAS_INLINE
1.540 + size_type index1 () const {
1.541 + return it1_;
1.542 + }
1.543 + BOOST_UBLAS_INLINE
1.544 + size_type index2 () const {
1.545 + return it2_;
1.546 + }
1.547 +
1.548 + // Assignment
1.549 + BOOST_UBLAS_INLINE
1.550 + iterator1 &operator = (const iterator1 &it) {
1.551 + container_reference<self_type>::assign (&it ());
1.552 + it1_ = it.it1_;
1.553 + it2_ = it.it2_;
1.554 + return *this;
1.555 + }
1.556 +
1.557 + // Comparison
1.558 + BOOST_UBLAS_INLINE
1.559 + bool operator == (const iterator1 &it) const {
1.560 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.561 + BOOST_UBLAS_CHECK (it2_ == it.it2_, external_logic ());
1.562 + return it1_ == it.it1_;
1.563 + }
1.564 + BOOST_UBLAS_INLINE
1.565 + bool operator < (const iterator1 &it) const {
1.566 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.567 + BOOST_UBLAS_CHECK (it2_ == it.it2_, external_logic ());
1.568 + return it1_ < it.it1_;
1.569 + }
1.570 +
1.571 + private:
1.572 + size_type it1_;
1.573 + size_type it2_;
1.574 +
1.575 + friend class const_iterator1;
1.576 + };
1.577 +#endif
1.578 +
1.579 + BOOST_UBLAS_INLINE
1.580 + iterator1 begin1 () {
1.581 + return find1 (0, 0, 0);
1.582 + }
1.583 + BOOST_UBLAS_INLINE
1.584 + iterator1 end1 () {
1.585 + return find1 (0, size_, 0);
1.586 + }
1.587 +
1.588 +#ifndef BOOST_UBLAS_USE_INDEXED_ITERATOR
1.589 + class const_iterator2:
1.590 + public container_const_reference<symmetric_matrix>,
1.591 + public random_access_iterator_base<dense_random_access_iterator_tag,
1.592 + const_iterator2, value_type> {
1.593 + public:
1.594 + typedef typename symmetric_matrix::value_type value_type;
1.595 + typedef typename symmetric_matrix::difference_type difference_type;
1.596 + typedef typename symmetric_matrix::const_reference reference;
1.597 + typedef const typename symmetric_matrix::pointer pointer;
1.598 +
1.599 + typedef const_iterator1 dual_iterator_type;
1.600 + typedef const_reverse_iterator1 dual_reverse_iterator_type;
1.601 +
1.602 + // Construction and destruction
1.603 + BOOST_UBLAS_INLINE
1.604 + const_iterator2 ():
1.605 + container_const_reference<self_type> (), it1_ (), it2_ () {}
1.606 + BOOST_UBLAS_INLINE
1.607 + const_iterator2 (const self_type &m, size_type it1, size_type it2):
1.608 + container_const_reference<self_type> (m), it1_ (it1), it2_ (it2) {}
1.609 + BOOST_UBLAS_INLINE
1.610 + const_iterator2 (const iterator2 &it):
1.611 + container_const_reference<self_type> (it ()), it1_ (it.it1_), it2_ (it.it2_) {}
1.612 +
1.613 + // Arithmetic
1.614 + BOOST_UBLAS_INLINE
1.615 + const_iterator2 &operator ++ () {
1.616 + ++ it2_;
1.617 + return *this;
1.618 + }
1.619 + BOOST_UBLAS_INLINE
1.620 + const_iterator2 &operator -- () {
1.621 + -- it2_;
1.622 + return *this;
1.623 + }
1.624 + BOOST_UBLAS_INLINE
1.625 + const_iterator2 &operator += (difference_type n) {
1.626 + it2_ += n;
1.627 + return *this;
1.628 + }
1.629 + BOOST_UBLAS_INLINE
1.630 + const_iterator2 &operator -= (difference_type n) {
1.631 + it2_ -= n;
1.632 + return *this;
1.633 + }
1.634 + BOOST_UBLAS_INLINE
1.635 + difference_type operator - (const const_iterator2 &it) const {
1.636 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.637 + BOOST_UBLAS_CHECK (it1_ == it.it1_, external_logic ());
1.638 + return it2_ - it.it2_;
1.639 + }
1.640 +
1.641 + // Dereference
1.642 + BOOST_UBLAS_INLINE
1.643 + const_reference operator * () const {
1.644 + return (*this) () (it1_, it2_);
1.645 + }
1.646 + BOOST_UBLAS_INLINE
1.647 + const_reference operator [] (difference_type n) const {
1.648 + return *(*this + n);
1.649 + }
1.650 +
1.651 +#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
1.652 + BOOST_UBLAS_INLINE
1.653 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.654 + typename self_type::
1.655 +#endif
1.656 + const_iterator1 begin () const {
1.657 + return (*this) ().find1 (1, 0, it2_);
1.658 + }
1.659 + BOOST_UBLAS_INLINE
1.660 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.661 + typename self_type::
1.662 +#endif
1.663 + const_iterator1 end () const {
1.664 + return (*this) ().find1 (1, (*this) ().size1 (), it2_);
1.665 + }
1.666 + BOOST_UBLAS_INLINE
1.667 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.668 + typename self_type::
1.669 +#endif
1.670 + const_reverse_iterator1 rbegin () const {
1.671 + return const_reverse_iterator1 (end ());
1.672 + }
1.673 + BOOST_UBLAS_INLINE
1.674 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.675 + typename self_type::
1.676 +#endif
1.677 + const_reverse_iterator1 rend () const {
1.678 + return const_reverse_iterator1 (begin ());
1.679 + }
1.680 +#endif
1.681 +
1.682 + // Indices
1.683 + BOOST_UBLAS_INLINE
1.684 + size_type index1 () const {
1.685 + return it1_;
1.686 + }
1.687 + BOOST_UBLAS_INLINE
1.688 + size_type index2 () const {
1.689 + return it2_;
1.690 + }
1.691 +
1.692 + // Assignment
1.693 + BOOST_UBLAS_INLINE
1.694 + const_iterator2 &operator = (const const_iterator2 &it) {
1.695 + container_const_reference<self_type>::assign (&it ());
1.696 + it1_ = it.it1_;
1.697 + it2_ = it.it2_;
1.698 + return *this;
1.699 + }
1.700 +
1.701 + // Comparison
1.702 + BOOST_UBLAS_INLINE
1.703 + bool operator == (const const_iterator2 &it) const {
1.704 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.705 + BOOST_UBLAS_CHECK (it1_ == it.it1_, external_logic ());
1.706 + return it2_ == it.it2_;
1.707 + }
1.708 + BOOST_UBLAS_INLINE
1.709 + bool operator < (const const_iterator2 &it) const {
1.710 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.711 + BOOST_UBLAS_CHECK (it1_ == it.it1_, external_logic ());
1.712 + return it2_ < it.it2_;
1.713 + }
1.714 +
1.715 + private:
1.716 + size_type it1_;
1.717 + size_type it2_;
1.718 + };
1.719 +#endif
1.720 +
1.721 + BOOST_UBLAS_INLINE
1.722 + const_iterator2 begin2 () const {
1.723 + return find2 (0, 0, 0);
1.724 + }
1.725 + BOOST_UBLAS_INLINE
1.726 + const_iterator2 end2 () const {
1.727 + return find2 (0, 0, size_);
1.728 + }
1.729 +
1.730 +#ifndef BOOST_UBLAS_USE_INDEXED_ITERATOR
1.731 + class iterator2:
1.732 + public container_reference<symmetric_matrix>,
1.733 + public random_access_iterator_base<packed_random_access_iterator_tag,
1.734 + iterator2, value_type> {
1.735 + public:
1.736 + typedef typename symmetric_matrix::value_type value_type;
1.737 + typedef typename symmetric_matrix::difference_type difference_type;
1.738 + typedef typename symmetric_matrix::reference reference;
1.739 + typedef typename symmetric_matrix::pointer pointer;
1.740 +
1.741 + typedef iterator1 dual_iterator_type;
1.742 + typedef reverse_iterator1 dual_reverse_iterator_type;
1.743 +
1.744 + // Construction and destruction
1.745 + BOOST_UBLAS_INLINE
1.746 + iterator2 ():
1.747 + container_reference<self_type> (), it1_ (), it2_ () {}
1.748 + BOOST_UBLAS_INLINE
1.749 + iterator2 (self_type &m, size_type it1, size_type it2):
1.750 + container_reference<self_type> (m), it1_ (it1), it2_ (it2) {}
1.751 +
1.752 + // Arithmetic
1.753 + BOOST_UBLAS_INLINE
1.754 + iterator2 &operator ++ () {
1.755 + ++ it2_;
1.756 + return *this;
1.757 + }
1.758 + BOOST_UBLAS_INLINE
1.759 + iterator2 &operator -- () {
1.760 + -- it2_;
1.761 + return *this;
1.762 + }
1.763 + BOOST_UBLAS_INLINE
1.764 + iterator2 &operator += (difference_type n) {
1.765 + it2_ += n;
1.766 + return *this;
1.767 + }
1.768 + BOOST_UBLAS_INLINE
1.769 + iterator2 &operator -= (difference_type n) {
1.770 + it2_ -= n;
1.771 + return *this;
1.772 + }
1.773 + BOOST_UBLAS_INLINE
1.774 + difference_type operator - (const iterator2 &it) const {
1.775 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.776 + BOOST_UBLAS_CHECK (it1_ == it.it1_, external_logic ());
1.777 + return it2_ - it.it2_;
1.778 + }
1.779 +
1.780 + // Dereference
1.781 + BOOST_UBLAS_INLINE
1.782 + reference operator * () const {
1.783 + return (*this) () (it1_, it2_);
1.784 + }
1.785 + BOOST_UBLAS_INLINE
1.786 + reference operator [] (difference_type n) const {
1.787 + return *(*this + n);
1.788 + }
1.789 +
1.790 +#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
1.791 + BOOST_UBLAS_INLINE
1.792 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.793 + typename self_type::
1.794 +#endif
1.795 + iterator1 begin () const {
1.796 + return (*this) ().find1 (1, 0, it2_);
1.797 + }
1.798 + BOOST_UBLAS_INLINE
1.799 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.800 + typename self_type::
1.801 +#endif
1.802 + iterator1 end () const {
1.803 + return (*this) ().find1 (1, (*this) ().size1 (), it2_);
1.804 + }
1.805 + BOOST_UBLAS_INLINE
1.806 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.807 + typename self_type::
1.808 +#endif
1.809 + reverse_iterator1 rbegin () const {
1.810 + return reverse_iterator1 (end ());
1.811 + }
1.812 + BOOST_UBLAS_INLINE
1.813 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.814 + typename self_type::
1.815 +#endif
1.816 + reverse_iterator1 rend () const {
1.817 + return reverse_iterator1 (begin ());
1.818 + }
1.819 +#endif
1.820 +
1.821 + // Indices
1.822 + BOOST_UBLAS_INLINE
1.823 + size_type index1 () const {
1.824 + return it1_;
1.825 + }
1.826 + BOOST_UBLAS_INLINE
1.827 + size_type index2 () const {
1.828 + return it2_;
1.829 + }
1.830 +
1.831 + // Assignment
1.832 + BOOST_UBLAS_INLINE
1.833 + iterator2 &operator = (const iterator2 &it) {
1.834 + container_reference<self_type>::assign (&it ());
1.835 + it1_ = it.it1_;
1.836 + it2_ = it.it2_;
1.837 + return *this;
1.838 + }
1.839 +
1.840 + // Comparison
1.841 + BOOST_UBLAS_INLINE
1.842 + bool operator == (const iterator2 &it) const {
1.843 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.844 + BOOST_UBLAS_CHECK (it1_ == it.it1_, external_logic ());
1.845 + return it2_ == it.it2_;
1.846 + }
1.847 + BOOST_UBLAS_INLINE
1.848 + bool operator < (const iterator2 &it) const {
1.849 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.850 + BOOST_UBLAS_CHECK (it1_ == it.it1_, external_logic ());
1.851 + return it2_ < it.it2_;
1.852 + }
1.853 +
1.854 + private:
1.855 + size_type it1_;
1.856 + size_type it2_;
1.857 +
1.858 + friend class const_iterator2;
1.859 + };
1.860 +#endif
1.861 +
1.862 + BOOST_UBLAS_INLINE
1.863 + iterator2 begin2 () {
1.864 + return find2 (0, 0, 0);
1.865 + }
1.866 + BOOST_UBLAS_INLINE
1.867 + iterator2 end2 () {
1.868 + return find2 (0, 0, size_);
1.869 + }
1.870 +
1.871 + // Reverse iterators
1.872 +
1.873 + BOOST_UBLAS_INLINE
1.874 + const_reverse_iterator1 rbegin1 () const {
1.875 + return const_reverse_iterator1 (end1 ());
1.876 + }
1.877 + BOOST_UBLAS_INLINE
1.878 + const_reverse_iterator1 rend1 () const {
1.879 + return const_reverse_iterator1 (begin1 ());
1.880 + }
1.881 +
1.882 + BOOST_UBLAS_INLINE
1.883 + reverse_iterator1 rbegin1 () {
1.884 + return reverse_iterator1 (end1 ());
1.885 + }
1.886 + BOOST_UBLAS_INLINE
1.887 + reverse_iterator1 rend1 () {
1.888 + return reverse_iterator1 (begin1 ());
1.889 + }
1.890 +
1.891 + BOOST_UBLAS_INLINE
1.892 + const_reverse_iterator2 rbegin2 () const {
1.893 + return const_reverse_iterator2 (end2 ());
1.894 + }
1.895 + BOOST_UBLAS_INLINE
1.896 + const_reverse_iterator2 rend2 () const {
1.897 + return const_reverse_iterator2 (begin2 ());
1.898 + }
1.899 +
1.900 + BOOST_UBLAS_INLINE
1.901 + reverse_iterator2 rbegin2 () {
1.902 + return reverse_iterator2 (end2 ());
1.903 + }
1.904 + BOOST_UBLAS_INLINE
1.905 + reverse_iterator2 rend2 () {
1.906 + return reverse_iterator2 (begin2 ());
1.907 + }
1.908 +
1.909 + private:
1.910 + size_type size_;
1.911 + array_type data_;
1.912 + };
1.913 +
1.914 +
1.915 + // Symmetric matrix adaptor class
1.916 + template<class M, class TRI>
1.917 + class symmetric_adaptor:
1.918 + public matrix_expression<symmetric_adaptor<M, TRI> > {
1.919 +
1.920 + typedef symmetric_adaptor<M, TRI> self_type;
1.921 + public:
1.922 +#ifdef BOOST_UBLAS_ENABLE_PROXY_SHORTCUTS
1.923 + using matrix_expression<self_type>::operator ();
1.924 +#endif
1.925 + typedef const M const_matrix_type;
1.926 + typedef M matrix_type;
1.927 + typedef TRI triangular_type;
1.928 + typedef typename M::size_type size_type;
1.929 + typedef typename M::difference_type difference_type;
1.930 + typedef typename M::value_type value_type;
1.931 + typedef typename M::const_reference const_reference;
1.932 + typedef typename boost::mpl::if_<boost::is_const<M>,
1.933 + typename M::const_reference,
1.934 + typename M::reference>::type reference;
1.935 + typedef typename boost::mpl::if_<boost::is_const<M>,
1.936 + typename M::const_closure_type,
1.937 + typename M::closure_type>::type matrix_closure_type;
1.938 + typedef const self_type const_closure_type;
1.939 + typedef self_type closure_type;
1.940 + // Replaced by _temporary_traits to avoid type requirements on M
1.941 + //typedef typename M::vector_temporary_type vector_temporary_type;
1.942 + //typedef typename M::matrix_temporary_type matrix_temporary_type;
1.943 + typedef typename storage_restrict_traits<typename M::storage_category,
1.944 + packed_proxy_tag>::storage_category storage_category;
1.945 + typedef typename M::orientation_category orientation_category;
1.946 +
1.947 + // Construction and destruction
1.948 + BOOST_UBLAS_INLINE
1.949 + symmetric_adaptor (matrix_type &data):
1.950 + matrix_expression<self_type> (),
1.951 + data_ (data) {
1.952 + BOOST_UBLAS_CHECK (data_.size1 () == data_.size2 (), bad_size ());
1.953 + }
1.954 + BOOST_UBLAS_INLINE
1.955 + symmetric_adaptor (const symmetric_adaptor &m):
1.956 + matrix_expression<self_type> (),
1.957 + data_ (m.data_) {
1.958 + BOOST_UBLAS_CHECK (data_.size1 () == data_.size2 (), bad_size ());
1.959 + }
1.960 +
1.961 + // Accessors
1.962 + BOOST_UBLAS_INLINE
1.963 + size_type size1 () const {
1.964 + return data_.size1 ();
1.965 + }
1.966 + BOOST_UBLAS_INLINE
1.967 + size_type size2 () const {
1.968 + return data_.size2 ();
1.969 + }
1.970 +
1.971 + // Storage accessors
1.972 + BOOST_UBLAS_INLINE
1.973 + const matrix_closure_type &data () const {
1.974 + return data_;
1.975 + }
1.976 + BOOST_UBLAS_INLINE
1.977 + matrix_closure_type &data () {
1.978 + return data_;
1.979 + }
1.980 +
1.981 + // Element access
1.982 +#ifndef BOOST_UBLAS_PROXY_CONST_MEMBER
1.983 + BOOST_UBLAS_INLINE
1.984 + const_reference operator () (size_type i, size_type j) const {
1.985 + BOOST_UBLAS_CHECK (i < size1 (), bad_index ());
1.986 + BOOST_UBLAS_CHECK (j < size2 (), bad_index ());
1.987 + if (triangular_type::other (i, j))
1.988 + return data () (i, j);
1.989 + else
1.990 + return data () (j, i);
1.991 + }
1.992 + BOOST_UBLAS_INLINE
1.993 + reference operator () (size_type i, size_type j) {
1.994 + BOOST_UBLAS_CHECK (i < size1 (), bad_index ());
1.995 + BOOST_UBLAS_CHECK (j < size2 (), bad_index ());
1.996 + if (triangular_type::other (i, j))
1.997 + return data () (i, j);
1.998 + else
1.999 + return data () (j, i);
1.1000 + }
1.1001 +#else
1.1002 + BOOST_UBLAS_INLINE
1.1003 + reference operator () (size_type i, size_type j) const {
1.1004 + BOOST_UBLAS_CHECK (i < size1 (), bad_index ());
1.1005 + BOOST_UBLAS_CHECK (j < size2 (), bad_index ());
1.1006 + if (triangular_type::other (i, j))
1.1007 + return data () (i, j);
1.1008 + else
1.1009 + return data () (j, i);
1.1010 + }
1.1011 +#endif
1.1012 +
1.1013 + // Assignment
1.1014 + BOOST_UBLAS_INLINE
1.1015 + symmetric_adaptor &operator = (const symmetric_adaptor &m) {
1.1016 + matrix_assign<scalar_assign, triangular_type> (*this, m);
1.1017 + return *this;
1.1018 + }
1.1019 + BOOST_UBLAS_INLINE
1.1020 + symmetric_adaptor &assign_temporary (symmetric_adaptor &m) {
1.1021 + *this = m;
1.1022 + return *this;
1.1023 + }
1.1024 + template<class AE>
1.1025 + BOOST_UBLAS_INLINE
1.1026 + symmetric_adaptor &operator = (const matrix_expression<AE> &ae) {
1.1027 + matrix_assign<scalar_assign, triangular_type> (*this, matrix<value_type> (ae));
1.1028 + return *this;
1.1029 + }
1.1030 + template<class AE>
1.1031 + BOOST_UBLAS_INLINE
1.1032 + symmetric_adaptor &assign (const matrix_expression<AE> &ae) {
1.1033 + matrix_assign<scalar_assign, triangular_type> (*this, ae);
1.1034 + return *this;
1.1035 + }
1.1036 + template<class AE>
1.1037 + BOOST_UBLAS_INLINE
1.1038 + symmetric_adaptor& operator += (const matrix_expression<AE> &ae) {
1.1039 + matrix_assign<scalar_assign, triangular_type> (*this, matrix<value_type> (*this + ae));
1.1040 + return *this;
1.1041 + }
1.1042 + template<class AE>
1.1043 + BOOST_UBLAS_INLINE
1.1044 + symmetric_adaptor &plus_assign (const matrix_expression<AE> &ae) {
1.1045 + matrix_assign<scalar_plus_assign, triangular_type> (*this, ae);
1.1046 + return *this;
1.1047 + }
1.1048 + template<class AE>
1.1049 + BOOST_UBLAS_INLINE
1.1050 + symmetric_adaptor& operator -= (const matrix_expression<AE> &ae) {
1.1051 + matrix_assign<scalar_assign, triangular_type> (*this, matrix<value_type> (*this - ae));
1.1052 + return *this;
1.1053 + }
1.1054 + template<class AE>
1.1055 + BOOST_UBLAS_INLINE
1.1056 + symmetric_adaptor &minus_assign (const matrix_expression<AE> &ae) {
1.1057 + matrix_assign<scalar_minus_assign, triangular_type> (*this, ae);
1.1058 + return *this;
1.1059 + }
1.1060 + template<class AT>
1.1061 + BOOST_UBLAS_INLINE
1.1062 + symmetric_adaptor& operator *= (const AT &at) {
1.1063 + matrix_assign_scalar<scalar_multiplies_assign> (*this, at);
1.1064 + return *this;
1.1065 + }
1.1066 + template<class AT>
1.1067 + BOOST_UBLAS_INLINE
1.1068 + symmetric_adaptor& operator /= (const AT &at) {
1.1069 + matrix_assign_scalar<scalar_divides_assign> (*this, at);
1.1070 + return *this;
1.1071 + }
1.1072 +
1.1073 + // Closure comparison
1.1074 + BOOST_UBLAS_INLINE
1.1075 + bool same_closure (const symmetric_adaptor &sa) const {
1.1076 + return (*this).data ().same_closure (sa.data ());
1.1077 + }
1.1078 +
1.1079 + // Swapping
1.1080 + BOOST_UBLAS_INLINE
1.1081 + void swap (symmetric_adaptor &m) {
1.1082 + if (this != &m)
1.1083 + matrix_swap<scalar_swap, triangular_type> (*this, m);
1.1084 + }
1.1085 + BOOST_UBLAS_INLINE
1.1086 + friend void swap (symmetric_adaptor &m1, symmetric_adaptor &m2) {
1.1087 + m1.swap (m2);
1.1088 + }
1.1089 +
1.1090 + // Iterator types
1.1091 + private:
1.1092 + // Use matrix iterator
1.1093 + typedef typename M::const_iterator1 const_subiterator1_type;
1.1094 + typedef typename boost::mpl::if_<boost::is_const<M>,
1.1095 + typename M::const_iterator1,
1.1096 + typename M::iterator1>::type subiterator1_type;
1.1097 + typedef typename M::const_iterator2 const_subiterator2_type;
1.1098 + typedef typename boost::mpl::if_<boost::is_const<M>,
1.1099 + typename M::const_iterator2,
1.1100 + typename M::iterator2>::type subiterator2_type;
1.1101 +
1.1102 + public:
1.1103 +#ifdef BOOST_UBLAS_USE_INDEXED_ITERATOR
1.1104 + typedef indexed_iterator1<self_type, packed_random_access_iterator_tag> iterator1;
1.1105 + typedef indexed_iterator2<self_type, packed_random_access_iterator_tag> iterator2;
1.1106 + typedef indexed_const_iterator1<self_type, dense_random_access_iterator_tag> const_iterator1;
1.1107 + typedef indexed_const_iterator2<self_type, dense_random_access_iterator_tag> const_iterator2;
1.1108 +#else
1.1109 + class const_iterator1;
1.1110 + class iterator1;
1.1111 + class const_iterator2;
1.1112 + class iterator2;
1.1113 +#endif
1.1114 + typedef reverse_iterator_base1<const_iterator1> const_reverse_iterator1;
1.1115 + typedef reverse_iterator_base1<iterator1> reverse_iterator1;
1.1116 + typedef reverse_iterator_base2<const_iterator2> const_reverse_iterator2;
1.1117 + typedef reverse_iterator_base2<iterator2> reverse_iterator2;
1.1118 +
1.1119 + // Element lookup
1.1120 + BOOST_UBLAS_INLINE
1.1121 + const_iterator1 find1 (int rank, size_type i, size_type j) const {
1.1122 + if (triangular_type::other (i, j)) {
1.1123 + if (triangular_type::other (size1 (), j)) {
1.1124 + return const_iterator1 (*this, 0, 0,
1.1125 + data ().find1 (rank, i, j), data ().find1 (rank, size1 (), j),
1.1126 + data ().find2 (rank, size2 (), size1 ()), data ().find2 (rank, size2 (), size1 ()));
1.1127 + } else {
1.1128 + return const_iterator1 (*this, 0, 1,
1.1129 + data ().find1 (rank, i, j), data ().find1 (rank, j, j),
1.1130 + data ().find2 (rank, j, j), data ().find2 (rank, j, size1 ()));
1.1131 + }
1.1132 + } else {
1.1133 + if (triangular_type::other (size1 (), j)) {
1.1134 + return const_iterator1 (*this, 1, 0,
1.1135 + data ().find1 (rank, j, j), data ().find1 (rank, size1 (), j),
1.1136 + data ().find2 (rank, j, i), data ().find2 (rank, j, j));
1.1137 + } else {
1.1138 + return const_iterator1 (*this, 1, 1,
1.1139 + data ().find1 (rank, size1 (), size2 ()), data ().find1 (rank, size1 (), size2 ()),
1.1140 + data ().find2 (rank, j, i), data ().find2 (rank, j, size1 ()));
1.1141 + }
1.1142 + }
1.1143 + }
1.1144 + BOOST_UBLAS_INLINE
1.1145 + iterator1 find1 (int rank, size_type i, size_type j) {
1.1146 + if (rank == 1)
1.1147 + i = triangular_type::mutable_restrict1 (i, j);
1.1148 + return iterator1 (*this, data ().find1 (rank, i, j));
1.1149 + }
1.1150 + BOOST_UBLAS_INLINE
1.1151 + const_iterator2 find2 (int rank, size_type i, size_type j) const {
1.1152 + if (triangular_type::other (i, j)) {
1.1153 + if (triangular_type::other (i, size2 ())) {
1.1154 + return const_iterator2 (*this, 1, 1,
1.1155 + data ().find1 (rank, size2 (), size1 ()), data ().find1 (rank, size2 (), size1 ()),
1.1156 + data ().find2 (rank, i, j), data ().find2 (rank, i, size2 ()));
1.1157 + } else {
1.1158 + return const_iterator2 (*this, 1, 0,
1.1159 + data ().find1 (rank, i, i), data ().find1 (rank, size2 (), i),
1.1160 + data ().find2 (rank, i, j), data ().find2 (rank, i, i));
1.1161 + }
1.1162 + } else {
1.1163 + if (triangular_type::other (i, size2 ())) {
1.1164 + return const_iterator2 (*this, 0, 1,
1.1165 + data ().find1 (rank, j, i), data ().find1 (rank, i, i),
1.1166 + data ().find2 (rank, i, i), data ().find2 (rank, i, size2 ()));
1.1167 + } else {
1.1168 + return const_iterator2 (*this, 0, 0,
1.1169 + data ().find1 (rank, j, i), data ().find1 (rank, size2 (), i),
1.1170 + data ().find2 (rank, size1 (), size2 ()), data ().find2 (rank, size2 (), size2 ()));
1.1171 + }
1.1172 + }
1.1173 + }
1.1174 + BOOST_UBLAS_INLINE
1.1175 + iterator2 find2 (int rank, size_type i, size_type j) {
1.1176 + if (rank == 1)
1.1177 + j = triangular_type::mutable_restrict2 (i, j);
1.1178 + return iterator2 (*this, data ().find2 (rank, i, j));
1.1179 + }
1.1180 +
1.1181 + // Iterators simply are indices.
1.1182 +
1.1183 +#ifndef BOOST_UBLAS_USE_INDEXED_ITERATOR
1.1184 + class const_iterator1:
1.1185 + public container_const_reference<symmetric_adaptor>,
1.1186 + public random_access_iterator_base<typename iterator_restrict_traits<
1.1187 + typename const_subiterator1_type::iterator_category, dense_random_access_iterator_tag>::iterator_category,
1.1188 + const_iterator1, value_type> {
1.1189 + public:
1.1190 + typedef typename const_subiterator1_type::value_type value_type;
1.1191 + typedef typename const_subiterator1_type::difference_type difference_type;
1.1192 + typedef typename const_subiterator1_type::reference reference;
1.1193 + typedef typename const_subiterator1_type::pointer pointer;
1.1194 +
1.1195 + typedef const_iterator2 dual_iterator_type;
1.1196 + typedef const_reverse_iterator2 dual_reverse_iterator_type;
1.1197 +
1.1198 + // Construction and destruction
1.1199 + BOOST_UBLAS_INLINE
1.1200 + const_iterator1 ():
1.1201 + container_const_reference<self_type> (),
1.1202 + begin_ (-1), end_ (-1), current_ (-1),
1.1203 + it1_begin_ (), it1_end_ (), it1_ (),
1.1204 + it2_begin_ (), it2_end_ (), it2_ () {}
1.1205 + BOOST_UBLAS_INLINE
1.1206 + const_iterator1 (const self_type &m, int begin, int end,
1.1207 + const const_subiterator1_type &it1_begin, const const_subiterator1_type &it1_end,
1.1208 + const const_subiterator2_type &it2_begin, const const_subiterator2_type &it2_end):
1.1209 + container_const_reference<self_type> (m),
1.1210 + begin_ (begin), end_ (end), current_ (begin),
1.1211 + it1_begin_ (it1_begin), it1_end_ (it1_end), it1_ (it1_begin_),
1.1212 + it2_begin_ (it2_begin), it2_end_ (it2_end), it2_ (it2_begin_) {
1.1213 + if (current_ == 0 && it1_ == it1_end_)
1.1214 + current_ = 1;
1.1215 + if (current_ == 1 && it2_ == it2_end_)
1.1216 + current_ = 0;
1.1217 + if ((current_ == 0 && it1_ == it1_end_) ||
1.1218 + (current_ == 1 && it2_ == it2_end_))
1.1219 + current_ = end_;
1.1220 + BOOST_UBLAS_CHECK (current_ == end_ ||
1.1221 + (current_ == 0 && it1_ != it1_end_) ||
1.1222 + (current_ == 1 && it2_ != it2_end_), internal_logic ());
1.1223 + }
1.1224 + // FIXME cannot compile
1.1225 + // iterator1 does not have these members!
1.1226 + BOOST_UBLAS_INLINE
1.1227 + const_iterator1 (const iterator1 &it):
1.1228 + container_const_reference<self_type> (it ()),
1.1229 + begin_ (it.begin_), end_ (it.end_), current_ (it.current_),
1.1230 + it1_begin_ (it.it1_begin_), it1_end_ (it.it1_end_), it1_ (it.it1_),
1.1231 + it2_begin_ (it.it2_begin_), it2_end_ (it.it2_end_), it2_ (it.it2_) {
1.1232 + BOOST_UBLAS_CHECK (current_ == end_ ||
1.1233 + (current_ == 0 && it1_ != it1_end_) ||
1.1234 + (current_ == 1 && it2_ != it2_end_), internal_logic ());
1.1235 + }
1.1236 +
1.1237 + // Arithmetic
1.1238 + BOOST_UBLAS_INLINE
1.1239 + const_iterator1 &operator ++ () {
1.1240 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1241 + if (current_ == 0) {
1.1242 + BOOST_UBLAS_CHECK (it1_ != it1_end_, internal_logic ());
1.1243 + ++ it1_;
1.1244 + if (it1_ == it1_end_ && end_ == 1) {
1.1245 + it2_ = it2_begin_;
1.1246 + current_ = 1;
1.1247 + }
1.1248 + } else /* if (current_ == 1) */ {
1.1249 + BOOST_UBLAS_CHECK (it2_ != it2_end_, internal_logic ());
1.1250 + ++ it2_;
1.1251 + if (it2_ == it2_end_ && end_ == 0) {
1.1252 + it1_ = it1_begin_;
1.1253 + current_ = 0;
1.1254 + }
1.1255 + }
1.1256 + return *this;
1.1257 + }
1.1258 + BOOST_UBLAS_INLINE
1.1259 + const_iterator1 &operator -- () {
1.1260 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1261 + if (current_ == 0) {
1.1262 + if (it1_ == it1_begin_ && begin_ == 1) {
1.1263 + it2_ = it2_end_;
1.1264 + BOOST_UBLAS_CHECK (it2_ != it2_begin_, internal_logic ());
1.1265 + -- it2_;
1.1266 + current_ = 1;
1.1267 + } else {
1.1268 + -- it1_;
1.1269 + }
1.1270 + } else /* if (current_ == 1) */ {
1.1271 + if (it2_ == it2_begin_ && begin_ == 0) {
1.1272 + it1_ = it1_end_;
1.1273 + BOOST_UBLAS_CHECK (it1_ != it1_begin_, internal_logic ());
1.1274 + -- it1_;
1.1275 + current_ = 0;
1.1276 + } else {
1.1277 + -- it2_;
1.1278 + }
1.1279 + }
1.1280 + return *this;
1.1281 + }
1.1282 + BOOST_UBLAS_INLINE
1.1283 + const_iterator1 &operator += (difference_type n) {
1.1284 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1285 + if (current_ == 0) {
1.1286 + size_type d = (std::min) (n, it1_end_ - it1_);
1.1287 + it1_ += d;
1.1288 + n -= d;
1.1289 + if (n > 0 || (end_ == 1 && it1_ == it1_end_)) {
1.1290 + BOOST_UBLAS_CHECK (end_ == 1, external_logic ());
1.1291 + d = (std::min) (n, it2_end_ - it2_begin_);
1.1292 + it2_ = it2_begin_ + d;
1.1293 + n -= d;
1.1294 + current_ = 1;
1.1295 + }
1.1296 + } else /* if (current_ == 1) */ {
1.1297 + size_type d = (std::min) (n, it2_end_ - it2_);
1.1298 + it2_ += d;
1.1299 + n -= d;
1.1300 + if (n > 0 || (end_ == 0 && it2_ == it2_end_)) {
1.1301 + BOOST_UBLAS_CHECK (end_ == 0, external_logic ());
1.1302 + d = (std::min) (n, it1_end_ - it1_begin_);
1.1303 + it1_ = it1_begin_ + d;
1.1304 + n -= d;
1.1305 + current_ = 0;
1.1306 + }
1.1307 + }
1.1308 + BOOST_UBLAS_CHECK (n == 0, external_logic ());
1.1309 + return *this;
1.1310 + }
1.1311 + BOOST_UBLAS_INLINE
1.1312 + const_iterator1 &operator -= (difference_type n) {
1.1313 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1314 + if (current_ == 0) {
1.1315 + size_type d = (std::min) (n, it1_ - it1_begin_);
1.1316 + it1_ -= d;
1.1317 + n -= d;
1.1318 + if (n > 0) {
1.1319 + BOOST_UBLAS_CHECK (end_ == 1, external_logic ());
1.1320 + d = (std::min) (n, it2_end_ - it2_begin_);
1.1321 + it2_ = it2_end_ - d;
1.1322 + n -= d;
1.1323 + current_ = 1;
1.1324 + }
1.1325 + } else /* if (current_ == 1) */ {
1.1326 + size_type d = (std::min) (n, it2_ - it2_begin_);
1.1327 + it2_ -= d;
1.1328 + n -= d;
1.1329 + if (n > 0) {
1.1330 + BOOST_UBLAS_CHECK (end_ == 0, external_logic ());
1.1331 + d = (std::min) (n, it1_end_ - it1_begin_);
1.1332 + it1_ = it1_end_ - d;
1.1333 + n -= d;
1.1334 + current_ = 0;
1.1335 + }
1.1336 + }
1.1337 + BOOST_UBLAS_CHECK (n == 0, external_logic ());
1.1338 + return *this;
1.1339 + }
1.1340 + BOOST_UBLAS_INLINE
1.1341 + difference_type operator - (const const_iterator1 &it) const {
1.1342 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.1343 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1344 + BOOST_UBLAS_CHECK (it.current_ == 0 || it.current_ == 1, internal_logic ());
1.1345 + BOOST_UBLAS_CHECK (/* begin_ == it.begin_ && */ end_ == it.end_, internal_logic ());
1.1346 + if (current_ == 0 && it.current_ == 0) {
1.1347 + return it1_ - it.it1_;
1.1348 + } else if (current_ == 0 && it.current_ == 1) {
1.1349 + if (end_ == 1 && it.end_ == 1) {
1.1350 + return (it1_ - it.it1_end_) + (it.it2_begin_ - it.it2_);
1.1351 + } else /* if (end_ == 0 && it.end_ == 0) */ {
1.1352 + return (it1_ - it.it1_begin_) + (it.it2_end_ - it.it2_);
1.1353 + }
1.1354 +
1.1355 + } else if (current_ == 1 && it.current_ == 0) {
1.1356 + if (end_ == 1 && it.end_ == 1) {
1.1357 + return (it2_ - it.it2_begin_) + (it.it1_end_ - it.it1_);
1.1358 + } else /* if (end_ == 0 && it.end_ == 0) */ {
1.1359 + return (it2_ - it.it2_end_) + (it.it1_begin_ - it.it1_);
1.1360 + }
1.1361 + }
1.1362 + /* current_ == 1 && it.current_ == 1 */ {
1.1363 + return it2_ - it.it2_;
1.1364 + }
1.1365 + }
1.1366 +
1.1367 + // Dereference
1.1368 + BOOST_UBLAS_INLINE
1.1369 + const_reference operator * () const {
1.1370 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1371 + if (current_ == 0) {
1.1372 + BOOST_UBLAS_CHECK (it1_ != it1_end_, internal_logic ());
1.1373 + return *it1_;
1.1374 + } else /* if (current_ == 1) */ {
1.1375 + BOOST_UBLAS_CHECK (it2_ != it2_end_, internal_logic ());
1.1376 + return *it2_;
1.1377 + }
1.1378 + }
1.1379 + BOOST_UBLAS_INLINE
1.1380 + const_reference operator [] (difference_type n) const {
1.1381 + return *(*this + n);
1.1382 + }
1.1383 +
1.1384 +#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
1.1385 + BOOST_UBLAS_INLINE
1.1386 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1387 + typename self_type::
1.1388 +#endif
1.1389 + const_iterator2 begin () const {
1.1390 + return (*this) ().find2 (1, index1 (), 0);
1.1391 + }
1.1392 + BOOST_UBLAS_INLINE
1.1393 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1394 + typename self_type::
1.1395 +#endif
1.1396 + const_iterator2 end () const {
1.1397 + return (*this) ().find2 (1, index1 (), (*this) ().size2 ());
1.1398 + }
1.1399 + BOOST_UBLAS_INLINE
1.1400 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1401 + typename self_type::
1.1402 +#endif
1.1403 + const_reverse_iterator2 rbegin () const {
1.1404 + return const_reverse_iterator2 (end ());
1.1405 + }
1.1406 + BOOST_UBLAS_INLINE
1.1407 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1408 + typename self_type::
1.1409 +#endif
1.1410 + const_reverse_iterator2 rend () const {
1.1411 + return const_reverse_iterator2 (begin ());
1.1412 + }
1.1413 +#endif
1.1414 +
1.1415 + // Indices
1.1416 + BOOST_UBLAS_INLINE
1.1417 + size_type index1 () const {
1.1418 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1419 + if (current_ == 0) {
1.1420 + BOOST_UBLAS_CHECK (it1_ != it1_end_, internal_logic ());
1.1421 + return it1_.index1 ();
1.1422 + } else /* if (current_ == 1) */ {
1.1423 + BOOST_UBLAS_CHECK (it2_ != it2_end_, internal_logic ());
1.1424 + return it2_.index2 ();
1.1425 + }
1.1426 + }
1.1427 + BOOST_UBLAS_INLINE
1.1428 + size_type index2 () const {
1.1429 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1430 + if (current_ == 0) {
1.1431 + BOOST_UBLAS_CHECK (it1_ != it1_end_, internal_logic ());
1.1432 + return it1_.index2 ();
1.1433 + } else /* if (current_ == 1) */ {
1.1434 + BOOST_UBLAS_CHECK (it2_ != it2_end_, internal_logic ());
1.1435 + return it2_.index1 ();
1.1436 + }
1.1437 + }
1.1438 +
1.1439 + // Assignment
1.1440 + BOOST_UBLAS_INLINE
1.1441 + const_iterator1 &operator = (const const_iterator1 &it) {
1.1442 + container_const_reference<self_type>::assign (&it ());
1.1443 + begin_ = it.begin_;
1.1444 + end_ = it.end_;
1.1445 + current_ = it.current_;
1.1446 + it1_begin_ = it.it1_begin_;
1.1447 + it1_end_ = it.it1_end_;
1.1448 + it1_ = it.it1_;
1.1449 + it2_begin_ = it.it2_begin_;
1.1450 + it2_end_ = it.it2_end_;
1.1451 + it2_ = it.it2_;
1.1452 + return *this;
1.1453 + }
1.1454 +
1.1455 + // Comparison
1.1456 + BOOST_UBLAS_INLINE
1.1457 + bool operator == (const const_iterator1 &it) const {
1.1458 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.1459 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1460 + BOOST_UBLAS_CHECK (it.current_ == 0 || it.current_ == 1, internal_logic ());
1.1461 + BOOST_UBLAS_CHECK (/* begin_ == it.begin_ && */ end_ == it.end_, internal_logic ());
1.1462 + return (current_ == 0 && it.current_ == 0 && it1_ == it.it1_) ||
1.1463 + (current_ == 1 && it.current_ == 1 && it2_ == it.it2_);
1.1464 + }
1.1465 + BOOST_UBLAS_INLINE
1.1466 + bool operator < (const const_iterator1 &it) const {
1.1467 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.1468 + return it - *this > 0;
1.1469 + }
1.1470 +
1.1471 + private:
1.1472 + int begin_;
1.1473 + int end_;
1.1474 + int current_;
1.1475 + const_subiterator1_type it1_begin_;
1.1476 + const_subiterator1_type it1_end_;
1.1477 + const_subiterator1_type it1_;
1.1478 + const_subiterator2_type it2_begin_;
1.1479 + const_subiterator2_type it2_end_;
1.1480 + const_subiterator2_type it2_;
1.1481 + };
1.1482 +#endif
1.1483 +
1.1484 + BOOST_UBLAS_INLINE
1.1485 + const_iterator1 begin1 () const {
1.1486 + return find1 (0, 0, 0);
1.1487 + }
1.1488 + BOOST_UBLAS_INLINE
1.1489 + const_iterator1 end1 () const {
1.1490 + return find1 (0, size1 (), 0);
1.1491 + }
1.1492 +
1.1493 +#ifndef BOOST_UBLAS_USE_INDEXED_ITERATOR
1.1494 + class iterator1:
1.1495 + public container_reference<symmetric_adaptor>,
1.1496 + public random_access_iterator_base<typename iterator_restrict_traits<
1.1497 + typename subiterator1_type::iterator_category, packed_random_access_iterator_tag>::iterator_category,
1.1498 + iterator1, value_type> {
1.1499 + public:
1.1500 + typedef typename subiterator1_type::value_type value_type;
1.1501 + typedef typename subiterator1_type::difference_type difference_type;
1.1502 + typedef typename subiterator1_type::reference reference;
1.1503 + typedef typename subiterator1_type::pointer pointer;
1.1504 +
1.1505 + typedef iterator2 dual_iterator_type;
1.1506 + typedef reverse_iterator2 dual_reverse_iterator_type;
1.1507 +
1.1508 + // Construction and destruction
1.1509 + BOOST_UBLAS_INLINE
1.1510 + iterator1 ():
1.1511 + container_reference<self_type> (), it1_ () {}
1.1512 + BOOST_UBLAS_INLINE
1.1513 + iterator1 (self_type &m, const subiterator1_type &it1):
1.1514 + container_reference<self_type> (m), it1_ (it1) {}
1.1515 +
1.1516 + // Arithmetic
1.1517 + BOOST_UBLAS_INLINE
1.1518 + iterator1 &operator ++ () {
1.1519 + ++ it1_;
1.1520 + return *this;
1.1521 + }
1.1522 + BOOST_UBLAS_INLINE
1.1523 + iterator1 &operator -- () {
1.1524 + -- it1_;
1.1525 + return *this;
1.1526 + }
1.1527 + BOOST_UBLAS_INLINE
1.1528 + iterator1 &operator += (difference_type n) {
1.1529 + it1_ += n;
1.1530 + return *this;
1.1531 + }
1.1532 + BOOST_UBLAS_INLINE
1.1533 + iterator1 &operator -= (difference_type n) {
1.1534 + it1_ -= n;
1.1535 + return *this;
1.1536 + }
1.1537 + BOOST_UBLAS_INLINE
1.1538 + difference_type operator - (const iterator1 &it) const {
1.1539 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.1540 + return it1_ - it.it1_;
1.1541 + }
1.1542 +
1.1543 + // Dereference
1.1544 + BOOST_UBLAS_INLINE
1.1545 + reference operator * () const {
1.1546 + return *it1_;
1.1547 + }
1.1548 + BOOST_UBLAS_INLINE
1.1549 + reference operator [] (difference_type n) const {
1.1550 + return *(*this + n);
1.1551 + }
1.1552 +
1.1553 +#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
1.1554 + BOOST_UBLAS_INLINE
1.1555 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1556 + typename self_type::
1.1557 +#endif
1.1558 + iterator2 begin () const {
1.1559 + return (*this) ().find2 (1, index1 (), 0);
1.1560 + }
1.1561 + BOOST_UBLAS_INLINE
1.1562 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1563 + typename self_type::
1.1564 +#endif
1.1565 + iterator2 end () const {
1.1566 + return (*this) ().find2 (1, index1 (), (*this) ().size2 ());
1.1567 + }
1.1568 + BOOST_UBLAS_INLINE
1.1569 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1570 + typename self_type::
1.1571 +#endif
1.1572 + reverse_iterator2 rbegin () const {
1.1573 + return reverse_iterator2 (end ());
1.1574 + }
1.1575 + BOOST_UBLAS_INLINE
1.1576 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1577 + typename self_type::
1.1578 +#endif
1.1579 + reverse_iterator2 rend () const {
1.1580 + return reverse_iterator2 (begin ());
1.1581 + }
1.1582 +#endif
1.1583 +
1.1584 + // Indices
1.1585 + BOOST_UBLAS_INLINE
1.1586 + size_type index1 () const {
1.1587 + return it1_.index1 ();
1.1588 + }
1.1589 + BOOST_UBLAS_INLINE
1.1590 + size_type index2 () const {
1.1591 + return it1_.index2 ();
1.1592 + }
1.1593 +
1.1594 + // Assignment
1.1595 + BOOST_UBLAS_INLINE
1.1596 + iterator1 &operator = (const iterator1 &it) {
1.1597 + container_reference<self_type>::assign (&it ());
1.1598 + it1_ = it.it1_;
1.1599 + return *this;
1.1600 + }
1.1601 +
1.1602 + // Comparison
1.1603 + BOOST_UBLAS_INLINE
1.1604 + bool operator == (const iterator1 &it) const {
1.1605 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.1606 + return it1_ == it.it1_;
1.1607 + }
1.1608 + BOOST_UBLAS_INLINE
1.1609 + bool operator < (const iterator1 &it) const {
1.1610 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.1611 + return it1_ < it.it1_;
1.1612 + }
1.1613 +
1.1614 + private:
1.1615 + subiterator1_type it1_;
1.1616 +
1.1617 + friend class const_iterator1;
1.1618 + };
1.1619 +#endif
1.1620 +
1.1621 + BOOST_UBLAS_INLINE
1.1622 + iterator1 begin1 () {
1.1623 + return find1 (0, 0, 0);
1.1624 + }
1.1625 + BOOST_UBLAS_INLINE
1.1626 + iterator1 end1 () {
1.1627 + return find1 (0, size1 (), 0);
1.1628 + }
1.1629 +
1.1630 +#ifndef BOOST_UBLAS_USE_INDEXED_ITERATOR
1.1631 + class const_iterator2:
1.1632 + public container_const_reference<symmetric_adaptor>,
1.1633 + public random_access_iterator_base<typename iterator_restrict_traits<
1.1634 + typename const_subiterator2_type::iterator_category, dense_random_access_iterator_tag>::iterator_category,
1.1635 + const_iterator2, value_type> {
1.1636 + public:
1.1637 + typedef typename const_subiterator2_type::value_type value_type;
1.1638 + typedef typename const_subiterator2_type::difference_type difference_type;
1.1639 + typedef typename const_subiterator2_type::reference reference;
1.1640 + typedef typename const_subiterator2_type::pointer pointer;
1.1641 +
1.1642 + typedef const_iterator1 dual_iterator_type;
1.1643 + typedef const_reverse_iterator1 dual_reverse_iterator_type;
1.1644 +
1.1645 + // Construction and destruction
1.1646 + BOOST_UBLAS_INLINE
1.1647 + const_iterator2 ():
1.1648 + container_const_reference<self_type> (),
1.1649 + begin_ (-1), end_ (-1), current_ (-1),
1.1650 + it1_begin_ (), it1_end_ (), it1_ (),
1.1651 + it2_begin_ (), it2_end_ (), it2_ () {}
1.1652 + BOOST_UBLAS_INLINE
1.1653 + const_iterator2 (const self_type &m, int begin, int end,
1.1654 + const const_subiterator1_type &it1_begin, const const_subiterator1_type &it1_end,
1.1655 + const const_subiterator2_type &it2_begin, const const_subiterator2_type &it2_end):
1.1656 + container_const_reference<self_type> (m),
1.1657 + begin_ (begin), end_ (end), current_ (begin),
1.1658 + it1_begin_ (it1_begin), it1_end_ (it1_end), it1_ (it1_begin_),
1.1659 + it2_begin_ (it2_begin), it2_end_ (it2_end), it2_ (it2_begin_) {
1.1660 + if (current_ == 0 && it1_ == it1_end_)
1.1661 + current_ = 1;
1.1662 + if (current_ == 1 && it2_ == it2_end_)
1.1663 + current_ = 0;
1.1664 + if ((current_ == 0 && it1_ == it1_end_) ||
1.1665 + (current_ == 1 && it2_ == it2_end_))
1.1666 + current_ = end_;
1.1667 + BOOST_UBLAS_CHECK (current_ == end_ ||
1.1668 + (current_ == 0 && it1_ != it1_end_) ||
1.1669 + (current_ == 1 && it2_ != it2_end_), internal_logic ());
1.1670 + }
1.1671 + // FIXME cannot compiler
1.1672 + // iterator2 does not have these members!
1.1673 + BOOST_UBLAS_INLINE
1.1674 + const_iterator2 (const iterator2 &it):
1.1675 + container_const_reference<self_type> (it ()),
1.1676 + begin_ (it.begin_), end_ (it.end_), current_ (it.current_),
1.1677 + it1_begin_ (it.it1_begin_), it1_end_ (it.it1_end_), it1_ (it.it1_),
1.1678 + it2_begin_ (it.it2_begin_), it2_end_ (it.it2_end_), it2_ (it.it2_) {
1.1679 + BOOST_UBLAS_CHECK (current_ == end_ ||
1.1680 + (current_ == 0 && it1_ != it1_end_) ||
1.1681 + (current_ == 1 && it2_ != it2_end_), internal_logic ());
1.1682 + }
1.1683 +
1.1684 + // Arithmetic
1.1685 + BOOST_UBLAS_INLINE
1.1686 + const_iterator2 &operator ++ () {
1.1687 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1688 + if (current_ == 0) {
1.1689 + BOOST_UBLAS_CHECK (it1_ != it1_end_, internal_logic ());
1.1690 + ++ it1_;
1.1691 + if (it1_ == it1_end_ && end_ == 1) {
1.1692 + it2_ = it2_begin_;
1.1693 + current_ = 1;
1.1694 + }
1.1695 + } else /* if (current_ == 1) */ {
1.1696 + BOOST_UBLAS_CHECK (it2_ != it2_end_, internal_logic ());
1.1697 + ++ it2_;
1.1698 + if (it2_ == it2_end_ && end_ == 0) {
1.1699 + it1_ = it1_begin_;
1.1700 + current_ = 0;
1.1701 + }
1.1702 + }
1.1703 + return *this;
1.1704 + }
1.1705 + BOOST_UBLAS_INLINE
1.1706 + const_iterator2 &operator -- () {
1.1707 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1708 + if (current_ == 0) {
1.1709 + if (it1_ == it1_begin_ && begin_ == 1) {
1.1710 + it2_ = it2_end_;
1.1711 + BOOST_UBLAS_CHECK (it2_ != it2_begin_, internal_logic ());
1.1712 + -- it2_;
1.1713 + current_ = 1;
1.1714 + } else {
1.1715 + -- it1_;
1.1716 + }
1.1717 + } else /* if (current_ == 1) */ {
1.1718 + if (it2_ == it2_begin_ && begin_ == 0) {
1.1719 + it1_ = it1_end_;
1.1720 + BOOST_UBLAS_CHECK (it1_ != it1_begin_, internal_logic ());
1.1721 + -- it1_;
1.1722 + current_ = 0;
1.1723 + } else {
1.1724 + -- it2_;
1.1725 + }
1.1726 + }
1.1727 + return *this;
1.1728 + }
1.1729 + BOOST_UBLAS_INLINE
1.1730 + const_iterator2 &operator += (difference_type n) {
1.1731 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1732 + if (current_ == 0) {
1.1733 + size_type d = (std::min) (n, it1_end_ - it1_);
1.1734 + it1_ += d;
1.1735 + n -= d;
1.1736 + if (n > 0 || (end_ == 1 && it1_ == it1_end_)) {
1.1737 + BOOST_UBLAS_CHECK (end_ == 1, external_logic ());
1.1738 + d = (std::min) (n, it2_end_ - it2_begin_);
1.1739 + it2_ = it2_begin_ + d;
1.1740 + n -= d;
1.1741 + current_ = 1;
1.1742 + }
1.1743 + } else /* if (current_ == 1) */ {
1.1744 + size_type d = (std::min) (n, it2_end_ - it2_);
1.1745 + it2_ += d;
1.1746 + n -= d;
1.1747 + if (n > 0 || (end_ == 0 && it2_ == it2_end_)) {
1.1748 + BOOST_UBLAS_CHECK (end_ == 0, external_logic ());
1.1749 + d = (std::min) (n, it1_end_ - it1_begin_);
1.1750 + it1_ = it1_begin_ + d;
1.1751 + n -= d;
1.1752 + current_ = 0;
1.1753 + }
1.1754 + }
1.1755 + BOOST_UBLAS_CHECK (n == 0, external_logic ());
1.1756 + return *this;
1.1757 + }
1.1758 + BOOST_UBLAS_INLINE
1.1759 + const_iterator2 &operator -= (difference_type n) {
1.1760 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1761 + if (current_ == 0) {
1.1762 + size_type d = (std::min) (n, it1_ - it1_begin_);
1.1763 + it1_ -= d;
1.1764 + n -= d;
1.1765 + if (n > 0) {
1.1766 + BOOST_UBLAS_CHECK (end_ == 1, external_logic ());
1.1767 + d = (std::min) (n, it2_end_ - it2_begin_);
1.1768 + it2_ = it2_end_ - d;
1.1769 + n -= d;
1.1770 + current_ = 1;
1.1771 + }
1.1772 + } else /* if (current_ == 1) */ {
1.1773 + size_type d = (std::min) (n, it2_ - it2_begin_);
1.1774 + it2_ -= d;
1.1775 + n -= d;
1.1776 + if (n > 0) {
1.1777 + BOOST_UBLAS_CHECK (end_ == 0, external_logic ());
1.1778 + d = (std::min) (n, it1_end_ - it1_begin_);
1.1779 + it1_ = it1_end_ - d;
1.1780 + n -= d;
1.1781 + current_ = 0;
1.1782 + }
1.1783 + }
1.1784 + BOOST_UBLAS_CHECK (n == 0, external_logic ());
1.1785 + return *this;
1.1786 + }
1.1787 + BOOST_UBLAS_INLINE
1.1788 + difference_type operator - (const const_iterator2 &it) const {
1.1789 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.1790 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1791 + BOOST_UBLAS_CHECK (it.current_ == 0 || it.current_ == 1, internal_logic ());
1.1792 + BOOST_UBLAS_CHECK (/* begin_ == it.begin_ && */ end_ == it.end_, internal_logic ());
1.1793 + if (current_ == 0 && it.current_ == 0) {
1.1794 + return it1_ - it.it1_;
1.1795 + } else if (current_ == 0 && it.current_ == 1) {
1.1796 + if (end_ == 1 && it.end_ == 1) {
1.1797 + return (it1_ - it.it1_end_) + (it.it2_begin_ - it.it2_);
1.1798 + } else /* if (end_ == 0 && it.end_ == 0) */ {
1.1799 + return (it1_ - it.it1_begin_) + (it.it2_end_ - it.it2_);
1.1800 + }
1.1801 +
1.1802 + } else if (current_ == 1 && it.current_ == 0) {
1.1803 + if (end_ == 1 && it.end_ == 1) {
1.1804 + return (it2_ - it.it2_begin_) + (it.it1_end_ - it.it1_);
1.1805 + } else /* if (end_ == 0 && it.end_ == 0) */ {
1.1806 + return (it2_ - it.it2_end_) + (it.it1_begin_ - it.it1_);
1.1807 + }
1.1808 + }
1.1809 + /* current_ == 1 && it.current_ == 1 */ {
1.1810 + return it2_ - it.it2_;
1.1811 + }
1.1812 + }
1.1813 +
1.1814 + // Dereference
1.1815 + BOOST_UBLAS_INLINE
1.1816 + const_reference operator * () const {
1.1817 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1818 + if (current_ == 0) {
1.1819 + BOOST_UBLAS_CHECK (it1_ != it1_end_, internal_logic ());
1.1820 + return *it1_;
1.1821 + } else /* if (current_ == 1) */ {
1.1822 + BOOST_UBLAS_CHECK (it2_ != it2_end_, internal_logic ());
1.1823 + return *it2_;
1.1824 + }
1.1825 + }
1.1826 + BOOST_UBLAS_INLINE
1.1827 + const_reference operator [] (difference_type n) const {
1.1828 + return *(*this + n);
1.1829 + }
1.1830 +
1.1831 +#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
1.1832 + BOOST_UBLAS_INLINE
1.1833 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1834 + typename self_type::
1.1835 +#endif
1.1836 + const_iterator1 begin () const {
1.1837 + return (*this) ().find1 (1, 0, index2 ());
1.1838 + }
1.1839 + BOOST_UBLAS_INLINE
1.1840 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1841 + typename self_type::
1.1842 +#endif
1.1843 + const_iterator1 end () const {
1.1844 + return (*this) ().find1 (1, (*this) ().size1 (), index2 ());
1.1845 + }
1.1846 + BOOST_UBLAS_INLINE
1.1847 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1848 + typename self_type::
1.1849 +#endif
1.1850 + const_reverse_iterator1 rbegin () const {
1.1851 + return const_reverse_iterator1 (end ());
1.1852 + }
1.1853 + BOOST_UBLAS_INLINE
1.1854 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.1855 + typename self_type::
1.1856 +#endif
1.1857 + const_reverse_iterator1 rend () const {
1.1858 + return const_reverse_iterator1 (begin ());
1.1859 + }
1.1860 +#endif
1.1861 +
1.1862 + // Indices
1.1863 + BOOST_UBLAS_INLINE
1.1864 + size_type index1 () const {
1.1865 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1866 + if (current_ == 0) {
1.1867 + BOOST_UBLAS_CHECK (it1_ != it1_end_, internal_logic ());
1.1868 + return it1_.index2 ();
1.1869 + } else /* if (current_ == 1) */ {
1.1870 + BOOST_UBLAS_CHECK (it2_ != it2_end_, internal_logic ());
1.1871 + return it2_.index1 ();
1.1872 + }
1.1873 + }
1.1874 + BOOST_UBLAS_INLINE
1.1875 + size_type index2 () const {
1.1876 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1877 + if (current_ == 0) {
1.1878 + BOOST_UBLAS_CHECK (it1_ != it1_end_, internal_logic ());
1.1879 + return it1_.index1 ();
1.1880 + } else /* if (current_ == 1) */ {
1.1881 + BOOST_UBLAS_CHECK (it2_ != it2_end_, internal_logic ());
1.1882 + return it2_.index2 ();
1.1883 + }
1.1884 + }
1.1885 +
1.1886 + // Assignment
1.1887 + BOOST_UBLAS_INLINE
1.1888 + const_iterator2 &operator = (const const_iterator2 &it) {
1.1889 + container_const_reference<self_type>::assign (&it ());
1.1890 + begin_ = it.begin_;
1.1891 + end_ = it.end_;
1.1892 + current_ = it.current_;
1.1893 + it1_begin_ = it.it1_begin_;
1.1894 + it1_end_ = it.it1_end_;
1.1895 + it1_ = it.it1_;
1.1896 + it2_begin_ = it.it2_begin_;
1.1897 + it2_end_ = it.it2_end_;
1.1898 + it2_ = it.it2_;
1.1899 + return *this;
1.1900 + }
1.1901 +
1.1902 + // Comparison
1.1903 + BOOST_UBLAS_INLINE
1.1904 + bool operator == (const const_iterator2 &it) const {
1.1905 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.1906 + BOOST_UBLAS_CHECK (current_ == 0 || current_ == 1, internal_logic ());
1.1907 + BOOST_UBLAS_CHECK (it.current_ == 0 || it.current_ == 1, internal_logic ());
1.1908 + BOOST_UBLAS_CHECK (/* begin_ == it.begin_ && */ end_ == it.end_, internal_logic ());
1.1909 + return (current_ == 0 && it.current_ == 0 && it1_ == it.it1_) ||
1.1910 + (current_ == 1 && it.current_ == 1 && it2_ == it.it2_);
1.1911 + }
1.1912 + BOOST_UBLAS_INLINE
1.1913 + bool operator < (const const_iterator2 &it) const {
1.1914 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.1915 + return it - *this > 0;
1.1916 + }
1.1917 +
1.1918 + private:
1.1919 + int begin_;
1.1920 + int end_;
1.1921 + int current_;
1.1922 + const_subiterator1_type it1_begin_;
1.1923 + const_subiterator1_type it1_end_;
1.1924 + const_subiterator1_type it1_;
1.1925 + const_subiterator2_type it2_begin_;
1.1926 + const_subiterator2_type it2_end_;
1.1927 + const_subiterator2_type it2_;
1.1928 + };
1.1929 +#endif
1.1930 +
1.1931 + BOOST_UBLAS_INLINE
1.1932 + const_iterator2 begin2 () const {
1.1933 + return find2 (0, 0, 0);
1.1934 + }
1.1935 + BOOST_UBLAS_INLINE
1.1936 + const_iterator2 end2 () const {
1.1937 + return find2 (0, 0, size2 ());
1.1938 + }
1.1939 +
1.1940 +#ifndef BOOST_UBLAS_USE_INDEXED_ITERATOR
1.1941 + class iterator2:
1.1942 + public container_reference<symmetric_adaptor>,
1.1943 + public random_access_iterator_base<typename iterator_restrict_traits<
1.1944 + typename subiterator2_type::iterator_category, packed_random_access_iterator_tag>::iterator_category,
1.1945 + iterator2, value_type> {
1.1946 + public:
1.1947 + typedef typename subiterator2_type::value_type value_type;
1.1948 + typedef typename subiterator2_type::difference_type difference_type;
1.1949 + typedef typename subiterator2_type::reference reference;
1.1950 + typedef typename subiterator2_type::pointer pointer;
1.1951 +
1.1952 + typedef iterator1 dual_iterator_type;
1.1953 + typedef reverse_iterator1 dual_reverse_iterator_type;
1.1954 +
1.1955 + // Construction and destruction
1.1956 + BOOST_UBLAS_INLINE
1.1957 + iterator2 ():
1.1958 + container_reference<self_type> (), it2_ () {}
1.1959 + BOOST_UBLAS_INLINE
1.1960 + iterator2 (self_type &m, const subiterator2_type &it2):
1.1961 + container_reference<self_type> (m), it2_ (it2) {}
1.1962 +
1.1963 + // Arithmetic
1.1964 + BOOST_UBLAS_INLINE
1.1965 + iterator2 &operator ++ () {
1.1966 + ++ it2_;
1.1967 + return *this;
1.1968 + }
1.1969 + BOOST_UBLAS_INLINE
1.1970 + iterator2 &operator -- () {
1.1971 + -- it2_;
1.1972 + return *this;
1.1973 + }
1.1974 + BOOST_UBLAS_INLINE
1.1975 + iterator2 &operator += (difference_type n) {
1.1976 + it2_ += n;
1.1977 + return *this;
1.1978 + }
1.1979 + BOOST_UBLAS_INLINE
1.1980 + iterator2 &operator -= (difference_type n) {
1.1981 + it2_ -= n;
1.1982 + return *this;
1.1983 + }
1.1984 + BOOST_UBLAS_INLINE
1.1985 + difference_type operator - (const iterator2 &it) const {
1.1986 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.1987 + return it2_ - it.it2_;
1.1988 + }
1.1989 +
1.1990 + // Dereference
1.1991 + BOOST_UBLAS_INLINE
1.1992 + reference operator * () const {
1.1993 + return *it2_;
1.1994 + }
1.1995 + BOOST_UBLAS_INLINE
1.1996 + reference operator [] (difference_type n) const {
1.1997 + return *(*this + n);
1.1998 + }
1.1999 +
1.2000 +#ifndef BOOST_UBLAS_NO_NESTED_CLASS_RELATION
1.2001 + BOOST_UBLAS_INLINE
1.2002 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.2003 + typename self_type::
1.2004 +#endif
1.2005 + iterator1 begin () const {
1.2006 + return (*this) ().find1 (1, 0, index2 ());
1.2007 + }
1.2008 + BOOST_UBLAS_INLINE
1.2009 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.2010 + typename self_type::
1.2011 +#endif
1.2012 + iterator1 end () const {
1.2013 + return (*this) ().find1 (1, (*this) ().size1 (), index2 ());
1.2014 + }
1.2015 + BOOST_UBLAS_INLINE
1.2016 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.2017 + typename self_type::
1.2018 +#endif
1.2019 + reverse_iterator1 rbegin () const {
1.2020 + return reverse_iterator1 (end ());
1.2021 + }
1.2022 + BOOST_UBLAS_INLINE
1.2023 +#ifdef BOOST_UBLAS_MSVC_NESTED_CLASS_RELATION
1.2024 + typename self_type::
1.2025 +#endif
1.2026 + reverse_iterator1 rend () const {
1.2027 + return reverse_iterator1 (begin ());
1.2028 + }
1.2029 +#endif
1.2030 +
1.2031 + // Indices
1.2032 + BOOST_UBLAS_INLINE
1.2033 + size_type index1 () const {
1.2034 + return it2_.index1 ();
1.2035 + }
1.2036 + BOOST_UBLAS_INLINE
1.2037 + size_type index2 () const {
1.2038 + return it2_.index2 ();
1.2039 + }
1.2040 +
1.2041 + // Assignment
1.2042 + BOOST_UBLAS_INLINE
1.2043 + iterator2 &operator = (const iterator2 &it) {
1.2044 + container_reference<self_type>::assign (&it ());
1.2045 + it2_ = it.it2_;
1.2046 + return *this;
1.2047 + }
1.2048 +
1.2049 + // Comparison
1.2050 + BOOST_UBLAS_INLINE
1.2051 + bool operator == (const iterator2 &it) const {
1.2052 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.2053 + return it2_ == it.it2_;
1.2054 + }
1.2055 + BOOST_UBLAS_INLINE
1.2056 + bool operator < (const iterator2 &it) const {
1.2057 + BOOST_UBLAS_CHECK (&(*this) () == &it (), external_logic ());
1.2058 + return it2_ < it.it2_;
1.2059 + }
1.2060 +
1.2061 + private:
1.2062 + subiterator2_type it2_;
1.2063 +
1.2064 + friend class const_iterator2;
1.2065 + };
1.2066 +#endif
1.2067 +
1.2068 + BOOST_UBLAS_INLINE
1.2069 + iterator2 begin2 () {
1.2070 + return find2 (0, 0, 0);
1.2071 + }
1.2072 + BOOST_UBLAS_INLINE
1.2073 + iterator2 end2 () {
1.2074 + return find2 (0, 0, size2 ());
1.2075 + }
1.2076 +
1.2077 + // Reverse iterators
1.2078 +
1.2079 + BOOST_UBLAS_INLINE
1.2080 + const_reverse_iterator1 rbegin1 () const {
1.2081 + return const_reverse_iterator1 (end1 ());
1.2082 + }
1.2083 + BOOST_UBLAS_INLINE
1.2084 + const_reverse_iterator1 rend1 () const {
1.2085 + return const_reverse_iterator1 (begin1 ());
1.2086 + }
1.2087 +
1.2088 + BOOST_UBLAS_INLINE
1.2089 + reverse_iterator1 rbegin1 () {
1.2090 + return reverse_iterator1 (end1 ());
1.2091 + }
1.2092 + BOOST_UBLAS_INLINE
1.2093 + reverse_iterator1 rend1 () {
1.2094 + return reverse_iterator1 (begin1 ());
1.2095 + }
1.2096 +
1.2097 + BOOST_UBLAS_INLINE
1.2098 + const_reverse_iterator2 rbegin2 () const {
1.2099 + return const_reverse_iterator2 (end2 ());
1.2100 + }
1.2101 + BOOST_UBLAS_INLINE
1.2102 + const_reverse_iterator2 rend2 () const {
1.2103 + return const_reverse_iterator2 (begin2 ());
1.2104 + }
1.2105 +
1.2106 + BOOST_UBLAS_INLINE
1.2107 + reverse_iterator2 rbegin2 () {
1.2108 + return reverse_iterator2 (end2 ());
1.2109 + }
1.2110 + BOOST_UBLAS_INLINE
1.2111 + reverse_iterator2 rend2 () {
1.2112 + return reverse_iterator2 (begin2 ());
1.2113 + }
1.2114 +
1.2115 + private:
1.2116 + matrix_closure_type data_;
1.2117 + };
1.2118 +
1.2119 + // Specialization for temporary_traits
1.2120 + template <class M, class TRI>
1.2121 + struct vector_temporary_traits< symmetric_adaptor<M, TRI> >
1.2122 + : vector_temporary_traits< M > {} ;
1.2123 + template <class M, class TRI>
1.2124 + struct vector_temporary_traits< const symmetric_adaptor<M, TRI> >
1.2125 + : vector_temporary_traits< M > {} ;
1.2126 +
1.2127 + template <class M, class TRI>
1.2128 + struct matrix_temporary_traits< symmetric_adaptor<M, TRI> >
1.2129 + : matrix_temporary_traits< M > {} ;
1.2130 + template <class M, class TRI>
1.2131 + struct matrix_temporary_traits< const symmetric_adaptor<M, TRI> >
1.2132 + : matrix_temporary_traits< M > {} ;
1.2133 +
1.2134 +}}}
1.2135 +
1.2136 +#endif