Index: branches/release/boost/multi_array/base.hpp =================================================================== --- a/branches/release/boost/multi_array/base.hpp +++ b/branches/release/boost/multi_array/base.hpp @@ -18,6 +18,7 @@ // functionality is acquired // +#include "boost/multi_array/collection_concept.hpp" #include "boost/multi_array/extent_range.hpp" #include "boost/multi_array/extent_gen.hpp" #include "boost/multi_array/index_range.hpp" @@ -82,5 +82,6 @@ class const_sub_array; -template + template class array_iterator; @@ -252,5 +253,17 @@ ///////////////////////////////////////////////////////////////////////// - +// Due to some imprecision in the C++ Standard, +// MSVC 2010 is broken in debug mode: it requires +// that an Output Iterator have output_iterator_tag in its iterator_category if +// that iterator is not bidirectional_iterator or random_access_iterator. +#if BOOST_WORKAROUND(BOOST_MSVC, >= 1600) +struct mutable_iterator_tag + : boost::random_access_traversal_tag, std::input_iterator_tag +{ + operator std::output_iterator_tag() const { + return std::output_iterator_tag(); + } +}; +#endif //////////////////////////////////////////////////////////////////////// @@ -302,6 +315,14 @@ // iterator support // - typedef array_iterator,reference> iterator; - typedef array_iterator,const_reference> const_iterator; +#if BOOST_WORKAROUND(BOOST_MSVC, >= 1600) + // Deal with VC 2010 output_iterator_tag requirement + typedef array_iterator,reference, + mutable_iterator_tag> iterator; +#else + typedef array_iterator,reference, + boost::random_access_traversal_tag> iterator; +#endif + typedef array_iterator,const_reference, + boost::random_access_traversal_tag> const_iterator; typedef ::boost::reverse_iterator reverse_iterator; @@ -322,5 +343,6 @@ const index* strides, const index* index_bases) const { - + boost::function_requires< + detail::multi_array::CollectionConcept >(); ignore_unused_variable_warning(index_bases); ignore_unused_variable_warning(extents); @@ -333,7 +355,13 @@ index offset = 0; - for (size_type n = 0; n != NumDims; ++n) - offset += indices[n] * strides[n]; - + { + typename IndexList::const_iterator i = indices.begin(); + size_type n = 0; + while (n != NumDims) { + offset += (*i) * strides[n]; + ++n; + ++i; + } + } return base[offset]; } Index: branches/release/boost/multi_array/concept_checks.hpp =================================================================== --- a/branches/release/boost/multi_array/concept_checks.hpp +++ b/branches/release/boost/multi_array/concept_checks.hpp @@ -132,4 +132,5 @@ function_requires< boost_concepts::ForwardTraversalConcept >(); function_requires< boost_concepts::ReadableIteratorConcept >(); + function_requires< boost::OutputIterator >(); // RG - a( CollectionArchetype) when available... Index: branches/release/boost/multi_array/iterator.hpp =================================================================== --- a/branches/release/boost/multi_array/iterator.hpp +++ b/branches/release/boost/multi_array/iterator.hpp @@ -45,14 +45,16 @@ }; -template +template class array_iterator; -template +template class array_iterator : public iterator_facade< - array_iterator + array_iterator , typename associated_types::value_type - , boost::random_access_traversal_tag + , IteratorCategory , Reference > @@ -70,5 +72,5 @@ typedef iterator_facade< - array_iterator + array_iterator , typename detail::multi_array::associated_types::value_type , boost::random_access_traversal_tag @@ -80,5 +82,5 @@ #ifndef BOOST_NO_MEMBER_TEMPLATE_FRIENDS - template + template friend class array_iterator; #else @@ -106,7 +108,7 @@ strides_(strides), index_base_(index_base) { } - template + template array_iterator( - const array_iterator& rhs + const array_iterator& rhs , typename boost::enable_if_convertible::type* = 0 )