Index: boost/multi_array.hpp =================================================================== --- boost/multi_array.hpp (revision 78399) +++ boost/multi_array.hpp (working copy) @@ -33,9 +33,9 @@ #include #include #include +#include - namespace boost { namespace detail { namespace multi_array { @@ -140,7 +140,7 @@ explicit multi_array() : super_type((T*)initial_base_,c_storage_order(), /*index_bases=*/0, /*extents=*/0) { - allocate_space(); + default_initialize(); } template @@ -155,9 +155,19 @@ super_type((T*)initial_base_,extents) { boost::function_requires< detail::multi_array::CollectionConcept >(); - allocate_space(); + default_initialize(); } + template + explicit multi_array( + ExtentList const& extents, + const T& value + ) : + super_type((T*)initial_base_,extents) { + boost::function_requires< + detail::multi_array::CollectionConcept >(); + default_initialize(value); + } template explicit multi_array(ExtentList const& extents, @@ -165,7 +175,7 @@ super_type((T*)initial_base_,extents,so) { boost::function_requires< detail::multi_array::CollectionConcept >(); - allocate_space(); + default_initialize(); } template @@ -175,24 +185,31 @@ super_type((T*)initial_base_,extents,so), allocator_(alloc) { boost::function_requires< detail::multi_array::CollectionConcept >(); - allocate_space(); + default_initialize(); } - explicit multi_array(const detail::multi_array ::extent_gen& ranges) : super_type((T*)initial_base_,ranges) { - allocate_space(); + default_initialize(); } + explicit multi_array(const detail::multi_array + ::extent_gen& ranges, + const T& value) : + super_type((T*)initial_base_,ranges) { + default_initialize(value); + } + + explicit multi_array(const detail::multi_array ::extent_gen& ranges, const general_storage_order& so) : super_type((T*)initial_base_,ranges,so) { - allocate_space(); + default_initialize(); } @@ -202,13 +219,12 @@ Allocator const& alloc) : super_type((T*)initial_base_,ranges,so), allocator_(alloc) { - allocate_space(); + default_initialize(); } multi_array(const multi_array& rhs) : super_type(rhs), allocator_(rhs.allocator_) { - allocate_space(); - boost::detail::multi_array::copy_n(rhs.base_,rhs.num_elements(),base_); + copy_initialize(rhs); } @@ -226,7 +242,7 @@ const general_storage_order& so = c_storage_order()) : super_type(0,so,rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); // Warning! storage order may change, hence the following copy technique. std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -237,7 +253,7 @@ const general_storage_order& so = c_storage_order()) : super_type(0,so,rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -248,7 +264,7 @@ const general_storage_order& so = c_storage_order()) : super_type(0,so,rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -259,7 +275,7 @@ multi_array(const const_multi_array_ref& rhs) : super_type(0,c_storage_order(),rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); // Warning! storage order may change, hence the following copy technique. std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -268,7 +284,7 @@ const general_storage_order& so) : super_type(0,so,rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); // Warning! storage order may change, hence the following copy technique. std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -277,7 +293,7 @@ const_sub_array& rhs) : super_type(0,c_storage_order(),rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -286,7 +302,7 @@ const general_storage_order& so) : super_type(0,so,rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -295,7 +311,7 @@ const_multi_array_view& rhs) : super_type(0,c_storage_order(),rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -304,7 +320,7 @@ const general_storage_order& so) : super_type(0,so,rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -314,7 +330,7 @@ multi_array(const multi_array_ref& rhs) : super_type(0,c_storage_order(),rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); // Warning! storage order may change, hence the following copy technique. std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -323,7 +339,7 @@ const general_storage_order& so) : super_type(0,so,rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); // Warning! storage order may change, hence the following copy technique. std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -333,7 +349,7 @@ sub_array& rhs) : super_type(0,c_storage_order(),rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -342,7 +358,7 @@ const general_storage_order& so) : super_type(0,so,rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -351,7 +367,7 @@ multi_array_view& rhs) : super_type(0,c_storage_order(),rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -360,7 +376,7 @@ const general_storage_order& so) : super_type(0,so,rhs.index_bases(),rhs.shape()) { - allocate_space(); + default_initialize(); std::copy(rhs.begin(),rhs.end(),this->begin()); } @@ -469,14 +485,24 @@ } private: + void allocate_space() { typename Allocator::const_pointer no_hint=0; base_ = allocator_.allocate(this->num_elements(),no_hint); this->set_base_ptr(base_); allocated_elements_ = this->num_elements(); - std::uninitialized_fill_n(base_,allocated_elements_,T()); } + void default_initialize(const T& value = T()) { + this->allocate_space(); + std::uninitialized_fill_n(base_,allocated_elements_,value); + } + + void copy_initialize(const multi_array& rhs) { + this->allocate_space(); + std::uninitialized_copy(rhs.base_,rhs.base_ + rhs.num_elements(),base_); + } + void deallocate_space() { if(base_) { for(T* i = base_; i != base_+allocated_elements_; ++i) Index: libs/multi_array/test/constructors.cpp =================================================================== --- libs/multi_array/test/constructors.cpp (revision 78399) +++ libs/multi_array/test/constructors.cpp (working copy) @@ -21,9 +21,18 @@ #include #include + +struct no_default +{ + explicit no_default(int i) {} +}; + void check_shape(const double&, std::size_t*, int*, unsigned int) {} +void check_shape(const no_default&, std::size_t*, int*, unsigned int) +{} + template void check_shape(const Array& A, std::size_t* sizes, @@ -37,7 +46,6 @@ check_shape(A[0], ++sizes, ++strides, num_elements / A.size()); } - bool equal(const double& a, const double& b) { return a == b; @@ -82,6 +90,12 @@ check_shape(C, &sizes[0], strides, num_elements); } + // Constructor 1, initialise with default value + { + boost::multi_array A(sizes, no_default(10)); + check_shape(A, &sizes[0], strides, num_elements); + } + // Constructor 1, fortran storage order and user-supplied allocator { typedef boost::multi_array