00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029 #ifndef TEUCHOS_ARRAY_VIEW_HPP
00030 #define TEUCHOS_ARRAY_VIEW_HPP
00031
00032
00033 #include "Teuchos_ArrayViewDecl.hpp"
00034 #include "Teuchos_ArrayRCP.hpp"
00035 #include "Teuchos_as.hpp"
00036
00037
00038 namespace Teuchos {
00039
00040
00041
00042
00043
00044 template<class T> inline
00045 ArrayView<T>::ArrayView( ENull )
00046 :ptr_(0), size_(0)
00047 {
00048 setUpIterators();
00049 }
00050
00051
00052 template<class T> inline
00053 ArrayView<T>::ArrayView( T* p, Ordinal size_in )
00054 :ptr_(p), size_(size_in)
00055 {
00056 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
00057 TEST_FOR_EXCEPT( p != 0 && size_in <= 0 );
00058 TEST_FOR_EXCEPT( p == 0 && size_in != 0 );
00059 setUpIterators();
00060 #endif
00061 }
00062
00063
00064 template<class T> inline
00065 ArrayView<T>::ArrayView(const ArrayView<T>& array)
00066 :ptr_(array.ptr_), size_(array.size_)
00067 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
00068 ,arcp_(array.arcp_)
00069 #endif
00070 {}
00071
00072
00073 template<class T> inline
00074 ArrayView<T>::ArrayView(
00075 std::vector<typename ConstTypeTraits<T>::NonConstType>& vec
00076 )
00077 : ptr_( vec.empty() ? 0 : &vec[0] ), size_(vec.size())
00078 {
00079 setUpIterators();
00080 }
00081
00082
00083 template<class T> inline
00084 ArrayView<T>::ArrayView(
00085 const std::vector<typename ConstTypeTraits<T>::NonConstType>& vec
00086 )
00087 : ptr_( vec.empty() ? 0 : &vec[0] ), size_(vec.size())
00088 {
00089 setUpIterators();
00090 }
00091
00092
00093 template<class T> inline
00094 ArrayView<T>& ArrayView<T>::operator=(const ArrayView<T>& array)
00095 {
00096 ptr_ = array.ptr_;
00097 size_ = array.size_;
00098 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
00099 arcp_ = array.arcp_;
00100 #endif
00101 return *this;
00102 }
00103
00104
00105 template<class T> inline
00106 ArrayView<T>::~ArrayView()
00107 {}
00108
00109
00110
00111
00112
00113 template<class T>
00114 inline
00115 bool ArrayView<T>::is_null() const
00116 {
00117 return ptr_ == 0;
00118 }
00119
00120
00121 template<class T> inline
00122 typename ArrayView<T>::Ordinal ArrayView<T>::size() const
00123 {
00124 debug_assert_valid_ptr();
00125 return size_;
00126 }
00127
00128
00129 template<typename T>
00130 std::string ArrayView<T>::toString() const
00131 {
00132
00133 using Teuchos::as;
00134 std::ostringstream ss;
00135
00136 debug_assert_valid_ptr();
00137
00138 ss << "{";
00139
00140 for (int i=0; i < as<int>(size()); ++i)
00141 {
00142 ss << operator[](i);
00143 if (i < size()-1) ss << ", ";
00144 }
00145 ss << "}";
00146
00147 return ss.str();
00148
00149 }
00150
00151
00152
00153
00154
00155 template<class T> inline
00156 T* ArrayView<T>::getRawPtr() const
00157 {
00158 debug_assert_valid_ptr();
00159 return ptr_;
00160 }
00161
00162
00163 template<class T> inline
00164 T& ArrayView<T>::operator[](Ordinal i) const
00165 {
00166 debug_assert_valid_ptr();
00167 debug_assert_in_range(i,1);
00168 return ptr_[i];
00169 }
00170
00171
00172 template<class T> inline
00173 T& ArrayView<T>::front() const
00174 {
00175 debug_assert_not_null();
00176 debug_assert_valid_ptr();
00177 return *ptr_;
00178 }
00179
00180
00181 template<class T> inline
00182 T& ArrayView<T>::back() const
00183 {
00184 debug_assert_not_null();
00185 debug_assert_valid_ptr();
00186 return *(ptr_+size_-1);
00187 }
00188
00189
00190
00191
00192
00193 template<class T> inline
00194 ArrayView<T> ArrayView<T>::view(Ordinal offset, Ordinal size_in) const
00195 {
00196 debug_assert_valid_ptr();
00197 debug_assert_in_range(offset, size_in);
00198 return ArrayView<T>(ptr_+offset,size_in);
00199
00200
00201 }
00202
00203
00204 template<class T> inline
00205 ArrayView<T> ArrayView<T>::operator()( Ordinal offset, Ordinal size_in ) const
00206 {
00207 return view(offset, size_in);
00208 }
00209
00210
00211 template<class T> inline
00212 const ArrayView<T>& ArrayView<T>::operator()() const
00213 {
00214 debug_assert_valid_ptr();
00215 return *this;
00216 }
00217
00218
00219 template<class T> inline
00220 ArrayView<const T> ArrayView<T>::getConst() const
00221 {
00222 debug_assert_valid_ptr();
00223 return ArrayView<const T>(ptr_,size_);
00224 }
00225
00226
00227 template<class T> inline
00228 ArrayView<T>::operator ArrayView<const T>() const
00229 {
00230 return getConst();
00231 }
00232
00233
00234
00235
00236
00237 template<class T>
00238 void ArrayView<T>::assign(const ArrayView<const T>& array) const
00239 {
00240 debug_assert_valid_ptr();
00241 debug_assert_not_null();
00242 if (this->getRawPtr()==array.getRawPtr() && this->size()==array.size())
00243 return;
00244 debug_assert_in_range(0,array.size());
00245 std::copy( array.begin(), array.end(), this->begin() );
00246
00247
00248 }
00249
00250
00251
00252
00253
00254 template<class T>
00255 typename ArrayView<T>::iterator ArrayView<T>::begin() const
00256 {
00257 debug_assert_valid_ptr();
00258 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
00259 return arcp_.create_weak();
00260 #else
00261 return ptr_;
00262 #endif
00263 }
00264
00265
00266 template<class T>
00267 typename ArrayView<T>::iterator ArrayView<T>::end() const
00268 {
00269 debug_assert_valid_ptr();
00270 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
00271 return arcp_.create_weak() + size_;
00272 #else
00273 return ptr_ + size_;
00274 #endif
00275 }
00276
00277
00278
00279
00280
00281 template<class T>
00282 const ArrayView<T>& ArrayView<T>::assert_not_null() const
00283 {
00284 if(!ptr_)
00285 throw_null_ptr_error(typeName(*this));
00286 return *this;
00287 }
00288
00289
00290 template<class T>
00291 const ArrayView<T>&
00292 ArrayView<T>::assert_in_range( Ordinal offset, Ordinal size_in ) const
00293 {
00294
00295 assert_not_null();
00296 TEST_FOR_EXCEPTION(
00297 !(
00298 ( 0 <= offset && offset+size_in <= this->size() )
00299 &&
00300 size_in >= 0
00301 ),
00302 Teuchos::RangeError,
00303 typeName(*this)<<"::assert_in_range():"
00304 " Error, [offset,offset+size) = ["<<offset<<","<<(offset+size_in)<<")"
00305 " does not lie in the range [0,"<<this->size()<<")!"
00306 );
00307 return*this;
00308 }
00309
00310
00311 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
00312
00313 template<class T>
00314 ArrayView<T>::ArrayView( const ArrayRCP<T> &arcp )
00315 : ptr_(arcp.getRawPtr()), size_(arcp.size()), arcp_(arcp)
00316 {}
00317
00318
00319 template<class T>
00320 ArrayView<T>::ArrayView( T* p, Ordinal size_in, const ArrayRCP<T> &arcp )
00321 : ptr_(p), size_(size_in), arcp_(arcp)
00322 {}
00323
00324
00325 #endif // HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
00326
00327
00328
00329
00330
00331 template<class T>
00332 void ArrayView<T>::setUpIterators()
00333 {
00334 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
00335 if (ptr_)
00336 arcp_ = arcp(ptr_, 0, size_, false);
00337
00338
00339 #endif
00340 }
00341
00342
00343 }
00344
00345
00346
00347
00348
00349
00350
00351 template<class T> inline
00352 Teuchos::ArrayView<T>
00353 Teuchos::arrayView( T* p, typename ArrayView<T>::Ordinal size )
00354 {
00355 return ArrayView<T>(p,size);
00356 }
00357
00358
00359 template<class T> inline
00360 Teuchos::ArrayView<T> Teuchos::arrayViewFromVector( std::vector<T>& vec )
00361 {
00362 return ArrayView<T>(vec);
00363 }
00364
00365
00366 template<class T> inline
00367 Teuchos::ArrayView<const T> Teuchos::arrayViewFromVector( const std::vector<T>& vec )
00368 {
00369 return ArrayView<const T>(vec);
00370 }
00371
00372
00373 #ifndef __sun
00374
00375 template<class T> inline
00376 std::vector<T> Teuchos::createVector( const ArrayView<T> &av )
00377 {
00378 std::vector<T> v(av.begin(), av.end());
00379 return v;
00380 }
00381
00382 #endif // __sun
00383
00384
00385 template<class T> inline
00386 std::vector<T> Teuchos::createVector( const ArrayView<const T> &av )
00387 {
00388 std::vector<T> v(av.begin(), av.end());
00389 return v;
00390 }
00391
00392
00393 template<class T> inline
00394 bool Teuchos::is_null( const ArrayView<T> &av )
00395 {
00396 return av.is_null();
00397 }
00398
00399
00400 template<class T>
00401 std::ostream& Teuchos::operator<<( std::ostream& out, const ArrayView<T>& p )
00402 {
00403 return out << p.toString();
00404 }
00405
00406
00407 template<class T2, class T1>
00408 REFCOUNTPTR_INLINE
00409 Teuchos::ArrayView<T2>
00410 Teuchos::av_reinterpret_cast(const ArrayView<T1>& p1)
00411 {
00412 typedef typename ArrayView<T1>::Ordinal Ordinal;
00413 const int sizeOfT1 = sizeof(T1);
00414 const int sizeOfT2 = sizeof(T2);
00415 Ordinal size2 = (p1.size()*sizeOfT1) / sizeOfT2;
00416 T2 *ptr2 = reinterpret_cast<T2*>(p1.getRawPtr());
00417 return ArrayView<T2>(
00418 ptr2, size2
00419 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
00420 ,arcp_reinterpret_cast<T2>(p1.access_private_arcp())
00421 #endif
00422 );
00423
00424 }
00425
00426
00427 #endif // TEUCHOS_ARRAY_VIEW_HPP