42 #ifndef TEUCHOS_ARRAY_H
43 #define TEUCHOS_ARRAY_H
50 #include "Teuchos_Assert.hpp"
52 #include "Teuchos_ArrayRCP.hpp"
53 #include "Teuchos_Tuple.hpp"
55 #include "Teuchos_Assert.hpp"
57 #if defined(HAVE_TEUCHOSCORE_CXX11) && defined(HAVE_TEUCHOS_ARRAY_BOUNDSCHECK) && defined(HAVE_TEUCHOS_THREAD_SAFE) && !defined(REMOVE_THREAD_PROTECTION_FOR_ARRAY)
59 #define USE_MUTEX_LOCK_FOR_ARRAY
72 template<
typename T>
class Array;
88 template<
typename T>
inline
96 template<
typename T>
inline
104 template<
typename T>
inline
112 template<
typename T>
inline
120 template<
typename T>
inline
128 template<
typename T>
inline
136 template<
typename T>
inline
204 template<
typename T2>
208 template<
typename T2>
212 template<
typename T2>
216 template<
typename T2>
220 template<
typename T2>
224 template<
typename T2>
228 template<
typename T2>
243 typedef typename std::vector<T>::pointer
pointer;
253 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
263 typedef typename std::vector<T>::iterator
iterator;
287 template<
typename InputIterator>
288 inline Array(InputIterator first, InputIterator last);
314 template<
typename InputIterator>
315 inline void assign(InputIterator first, InputIterator last);
341 inline bool empty()
const;
369 template<
typename InputIterator>
370 inline void insert(
iterator position, InputIterator first, InputIterator last);
393 inline void remove(
int i);
399 inline int length()
const;
402 inline std::string
toString()
const;
418 inline Array(
const std::vector<T> &v );
421 inline std::vector<T>
toVector()
const;
497 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
501 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
502 mutable std::mutex mutex_lock;
508 inline std::vector<T>& vec(
509 bool isStructureBeingModified =
false,
510 bool activeIter =
false
513 inline const std::vector<T>& vec()
const;
515 inline typename std::vector<T>::iterator
518 inline void assertIndex(
size_type i)
const;
520 inline void assertNotNull()
const;
533 if (
is_null(v) || !v->size() )
535 return arcpWithEmbeddedObjPostDestroy<T,RCP<Array<T> > >(
536 &(*v)[0], 0, v->size(),
550 if (
is_null(v) || !v->size() )
552 return arcpWithEmbeddedObjPostDestroy<const T,RCP<const Array<T> > >(
553 &(*v)[0], 0, v->size(),
608 std::ostream& operator<<(std::ostream& os,
const Array<T>& array);
615 template<
typename T>
inline
616 int hashCode(
const Array<T>& array);
625 template<
typename T>
inline
626 std::vector<T> createVector(
const Array<T> &a );
634 std::string toString(
const Array<T>& array);
689 Array<T> fromStringToArray(
const std::string& arrayStr);
697 std::istringstream& operator>> (std::istringstream& in,
Array<T>& array){
698 array = fromStringToArray<T>(in.str());
707 template<
typename T>
inline
762 static std::string name(){
763 std::string formatString = getArrayTypeNameTraitsFormat();
764 size_t starPos = formatString.find(
"*");
765 std::string prefix = formatString.substr(0,starPos);
766 std::string postFix = formatString.substr(starPos+1);
769 static std::string concreteName(
const Array<T>&)
788 template<
typename T>
inline
790 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
791 : vec_(
rcp(
new std::vector<T>()))
796 template<
typename T>
inline
798 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
799 vec_(
rcp(new std::vector<T>(n,value)))
806 template<
typename T>
inline
808 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
809 vec_(
rcp(new std::vector<T>(*x.vec_)))
816 template<
typename T>
template<
typename InputIterator>
inline
818 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
819 vec_(
rcp(new std::vector<T>(first, last)))
826 template<
typename T>
inline
831 template<
typename T>
inline
833 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
834 : vec_(
rcp(
new std::vector<T>()))
837 insert(begin(), a.begin(), a.end());
845 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
846 : vec_(
rcp(
new std::vector<T>()))
849 insert(begin(), t.
begin(), t.
end());
853 template<
typename T>
inline
856 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
857 std::lock_guard<std::mutex> lockGuard(mutex_lock);
867 template<
typename T>
inline
870 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
871 std::lock_guard<std::mutex> lockGuard(mutex_lock);
873 vec(
true).assign(n,val);
877 template<
typename T>
template<
typename InputIterator>
inline
880 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
881 std::lock_guard<std::mutex> lockGuard(mutex_lock);
883 vec(
true).assign(first,last);
887 template<
typename T>
inline
891 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
893 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
894 std::lock_guard<std::mutex> lockGuard(mutex_lock);
899 extern_arcp_ =
arcp(vec_);
904 return extern_arcp_.create_weak();
906 return vec().begin();
911 template<
typename T>
inline
915 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
916 return begin() +
size();
922 template<
typename T>
inline
926 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
928 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
929 std::lock_guard<std::mutex> lockGuard(mutex_lock);
939 extern_arcp_ =
arcp(vec_);
943 extern_carcp_ = extern_arcp_.create_weak();
948 return extern_carcp_.create_weak();
950 return vec().begin();
955 template<
typename T>
inline
959 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
960 return begin() +
size();
967 template<
typename T>
inline
971 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
974 return vec().rbegin();
979 template<
typename T>
inline
983 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
991 template<
typename T>
inline
995 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
998 return vec().rbegin();
1003 template<
typename T>
inline
1007 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1010 return vec().rend();
1015 template<
typename T>
inline
1019 return vec().
size();
1023 template<
typename T>
inline
1027 return std::numeric_limits<size_type>::max();
1031 template<
typename T>
inline
1035 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1036 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1038 vec(
true).resize(new_size,x);
1042 template<
typename T>
inline
1050 template<
typename T>
inline
1053 return vec().
empty();
1057 template<
typename T>
inline
1060 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1061 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1063 vec(
true).reserve(n);
1067 template<
typename T>
inline
1071 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1078 template<
typename T>
inline
1082 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1089 template<
typename T>
inline
1093 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1100 template<
typename T>
inline
1104 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1111 template<
typename T>
inline
1115 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1118 return vec().front();
1122 template<
typename T>
inline
1126 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1129 return vec().front();
1133 template<
typename T>
inline
1137 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1140 return vec().back();
1144 template<
typename T>
inline
1148 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1151 return vec().back();
1155 template<
typename T>
inline
1158 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1159 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1161 vec(
true).push_back(x);
1165 template<
typename T>
inline
1168 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1171 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1172 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1174 vec(
true).pop_back();
1190 template<
typename T>
inline
1194 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1196 const typename std::vector<T>::iterator raw_poss = raw_position(position);
1198 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1200 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1202 vec(
true,
true).insert(raw_poss, x);
1203 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1208 return vec_.insert(position, x);
1213 template<
typename T>
inline
1216 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1217 const typename std::vector<T>::iterator raw_poss = raw_position(position);
1218 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1219 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1221 vec(
true,
true).insert(raw_poss, n, x);
1223 vec_.insert(position, n, x);
1228 template<
typename T>
template<
typename InputIterator>
inline
1231 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1232 const typename std::vector<T>::iterator raw_poss = raw_position(position);
1233 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1234 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1236 vec(
true,
true).insert(raw_poss, first, last);
1238 vec_.insert(position, first, last);
1243 template<
typename T>
inline
1247 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1250 const typename std::vector<T>::iterator raw_poss = raw_position(position);
1252 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1254 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1256 vec(
true,
true).erase(raw_poss);
1257 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1262 return vec_.erase(position);
1267 template<
typename T>
inline
1271 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1279 const typename std::vector<T>::iterator raw_first = raw_position(first);
1280 const typename std::vector<T>::iterator raw_last = raw_position(last);
1282 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1284 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1286 vec(
true,
true).erase(raw_first,raw_last);
1287 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1292 return vec_.erase(first,last);
1297 template<
typename T>
inline
1300 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1301 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1303 vec(
true).swap(x.vec());
1307 template<
typename T>
inline
1310 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1311 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1320 template<
typename T>
inline
1328 template<
typename T>
inline
1331 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1335 this->erase( this->begin() + i );
1339 template<
typename T>
inline
1342 return static_cast<int> (this->
size ());
1346 template<
typename T>
inline
1353 template<
typename T>
inline
1356 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1364 template<
typename T>
inline
1367 return (
size() ? &(*
this)[0] : 0 );
1371 template<
typename T>
inline
1374 return (
size() ? &(*
this)[0] : 0 );
1381 template<
typename T>
inline
1383 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1384 vec_(new std::vector<T>(v))
1391 template<
typename T>
inline
1395 return std::vector<T>();
1396 std::vector<T> v(begin(),end());
1401 template<
typename T>
inline
1404 #ifdef USE_MUTEX_LOCK_FOR_ARRAY
1405 std::lock_guard<std::mutex> lockGuard(mutex_lock);
1415 template<
typename T>
inline
1419 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1420 return ArrayView<T>(this->begin().persistingView(offset, size_in));
1422 return arrayView( &vec()[offset], size_in );
1425 return Teuchos::null;
1429 template<
typename T>
inline
1433 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1436 return arrayView( &vec()[offset], size_in );
1439 return Teuchos::null;
1446 template<
typename T>
inline
1449 return view(offset, size_in);
1453 template<
typename T>
inline
1456 return view(offset, size_in);
1460 template<
typename T>
inline
1465 return this->view(0,
size());
1469 template<
typename T>
inline
1474 return this->view(0,
size());
1478 template<
typename T>
inline
1481 return this->operator()();
1485 template<
typename T>
inline
1488 return this->operator()();
1495 template<
typename T>
1497 Array<T>::vec(
bool isStructureBeingModified,
bool activeIter )
1499 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1501 if (isStructureBeingModified) {
1509 extern_arcp_ =
null;
1510 extern_carcp_ =
null;
1515 (void)isStructureBeingModified;
1522 template<
typename T>
inline
1523 const std::vector<T>&
1524 Array<T>::vec()
const
1526 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1534 template<
typename T>
inline
1535 typename std::vector<T>::iterator
1536 Array<T>::raw_position( iterator position )
1538 #ifdef HAVE_TEUCHOS_ARRAY_BOUNDSCHECK
1539 const iterator first = this->begin();
1540 const iterator last = this->end();
1542 !(first <= position && position <= last), DanglingReferenceError,
1543 "Error, this iterator is no longer valid for this Aray!"
1548 return vec_->begin() + (position - this->begin());
1555 template<
typename T>
inline
1556 void Array<T>::assertIndex(size_type i)
const
1559 !( 0 <= i && i <
size() ), RangeError,
1560 "Array<T>::assertIndex(i): i="<<i<<
" out of range [0, "<<
size() <<
")"
1565 template<
typename T>
inline
1566 void Array<T>::assertNotNull()
const
1569 !
size(), NullReferenceError,
1570 typeName(*
this)<<
"::assertNotNull(): "
1571 "Error, the array has size zero!"
1582 template<
typename T>
inline
1583 bool Teuchos::operator==(
const Array<T> &a1,
const Array<T> &a2 )
1584 {
return (a1.vec() == a2.vec()); }
1587 template<
typename T>
inline
1588 bool Teuchos::operator!=(
const Array<T> &a1,
const Array<T> &a2 )
1589 {
return (a1.vec() != a2.vec()); }
1592 template<
typename T>
inline
1593 void Teuchos::swap( Array<T> &a1, Array<T> &a2 )
1597 template<
typename T>
inline
1598 bool Teuchos::operator<(
const Array<T> &a1,
const Array<T> &a2 )
1599 {
return (a1.vec() < a2.vec()); }
1602 template<
typename T>
inline
1603 bool Teuchos::operator<=(
const Array<T> &a1,
const Array<T> &a2 )
1604 {
return (a1.vec() <= a2.vec()); }
1607 template<
typename T>
inline
1608 bool Teuchos::operator>(
const Array<T> &a1,
const Array<T> &a2 )
1609 {
return (a1.vec() > a2.vec()); }
1612 template<
typename T>
inline
1613 bool Teuchos::operator>=(
const Array<T> &a1,
const Array<T> &a2 )
1614 {
return (a1.vec() >= a2.vec()); }
1617 template<
typename T>
inline
1618 std::ostream& Teuchos::operator<<(
1619 std::ostream& os,
const Array<T>& array
1622 return os << Teuchos::toString(array);
1626 template<
typename T>
inline
1627 int Teuchos::hashCode(
const Array<T>& array)
1629 int rtn =
hashCode(array.length());
1630 for (
int i=0; i<array.length(); i++)
1639 size_t maxIntBeforeWrap = std::numeric_limits<int>::max();
1640 maxIntBeforeWrap ++;
1641 rtn += maxIntBeforeWrap;
1647 template<
typename T>
inline
1648 std::vector<T> Teuchos::createVector(
const Array<T> &a )
1650 return a.toVector();
1654 template<
typename T>
inline
1655 std::string Teuchos::toString(
const Array<T>& array)
1657 return array.toString();
1661 template<
typename T>
1663 Teuchos::fromStringToArray(
const std::string& arrayStr)
1665 const std::string str = Utils::trimWhiteSpace(arrayStr);
1666 std::istringstream iss(str);
1668 ( str[0]!=
'{' || str[str.length()-1] !=
'}' )
1669 ,InvalidArrayStringRepresentation
1670 ,
"Error, the std::string:\n"
1674 "is not a valid array represntation!"
1681 while( !iss.eof() ) {
1683 std::string entryStr;
1684 std::getline(iss,entryStr,
',');
1693 entryStr = Utils::trimWhiteSpace(entryStr);
1695 0 == entryStr.length(),
1696 InvalidArrayStringRepresentation,
1697 "Error, the std::string:\n"
1701 "is not a valid array represntation because it has an empty array entry!"
1705 bool found_end =
false;
1706 if(entryStr[entryStr.length()-1]==
'}') {
1707 entryStr = entryStr.substr(0,entryStr.length()-1);
1709 if( entryStr.length()==0 && a.size()==0 )
1713 std::istringstream entryiss(entryStr);
1715 Teuchos::extractDataFromISS( entryiss, entry );
1724 found_end && !iss.eof()
1725 ,InvalidArrayStringRepresentation
1726 ,
"Error, the std::string:\n"
1730 "is not a valid array represntation!"
1737 #endif // TEUCHOS_ARRAY_H