16#if __cplusplus > 201402L
17#define R__RVEC_NODISCARD [[nodiscard]]
19#define R__RVEC_NODISCARD
24 #ifndef _USE_MATH_DEFINES
25 #define _USE_MATH_DEFINES
28 #undef _USE_MATH_DEFINES
30 #define _VECOPS_USE_EXTERN_TEMPLATES false
32 #define _VECOPS_USE_EXTERN_TEMPLATES true
53#include <vdt/vdtMath.h>
70template <
typename... T>
73 constexpr const auto nArgs =
sizeof...(T);
74 const std::size_t sizes[] = {vs.
size()...};
76 for (
auto i = 1UL; i < nArgs; i++) {
77 if (sizes[0] == sizes[i])
80 msg +=
": input RVec instances have different lengths!";
81 throw std::runtime_error(msg);
87template <
typename F,
typename... T>
93 for (
auto i = 0UL; i <
size; i++)
99template <
typename Tuple_t, std::size_t... Is>
101 ->
decltype(
MapImpl(std::get<std::tuple_size<Tuple_t>::value - 1>(t), std::get<Is>(t)...))
103 constexpr const auto tupleSizeM1 = std::tuple_size<Tuple_t>::value - 1;
104 return MapImpl(std::get<tupleSizeM1>(t), std::get<Is>(t)...);
136 static constexpr size_t SizeTypeMax() {
return std::numeric_limits<Size_T>::max(); }
139 SmallVectorBase(
void *FirstEl,
size_t TotalCapacity) : fBeginX(FirstEl), fCapacity(TotalCapacity) {}
144 void grow_pod(
void *FirstEl,
size_t MinSize,
size_t TSize);
148 static void report_size_overflow(
size_t MinSize);
151 static void report_at_maximum_capacity();
154 bool Owns()
const {
return fCapacity != -1; }
173 if (
N > capacity()) {
174 throw std::runtime_error(
"Setting size to a value greater than capacity.");
182 void shrink_to_fit() { }
189 alignas(T)
char FirstEl[
sizeof(T)];
202 return const_cast<void *
>(
reinterpret_cast<const void *
>(
reinterpret_cast<const char *
>(
this) +
210 void grow_pod(
size_t MinSize,
size_t TSize) { Base::grow_pod(getFirstEl(), MinSize, TSize); }
214 bool isSmall()
const {
return this->fBeginX == getFirstEl(); }
219 this->fBeginX = getFirstEl();
222 this->
fSize = this->fCapacity = 0;
242 using Base::capacity;
275 throw std::runtime_error(
"`front` called on an empty RVec");
283 throw std::runtime_error(
"`front` called on an empty RVec");
291 throw std::runtime_error(
"`back` called on an empty RVec");
299 throw std::runtime_error(
"`back` called on an empty RVec");
313template <
typename T,
bool = (std::is_trivially_copy_constructible<T>::value) &&
314 (std::is_trivially_move_constructible<T>::value) &&
315 std::is_trivially_destructible<T>::value>
330 template <
typename It1,
typename It2>
333 std::uninitialized_copy(std::make_move_iterator(
I), std::make_move_iterator(E), Dest);
338 template <
typename It1,
typename It2>
341 std::uninitialized_copy(
I, E, Dest);
354 ::new ((
void *)this->end()) T(Elt);
355 this->set_size(this->
size() + 1);
362 ::new ((
void *)this->end()) T(::std::move(Elt));
363 this->set_size(this->
size() + 1);
368 this->set_size(this->
size() - 1);
374template <
typename T,
bool TriviallyCopyable>
379 if (MinSize > this->SizeTypeMax())
380 this->report_size_overflow(MinSize);
386 if (this->capacity() == this->SizeTypeMax())
387 this->report_at_maximum_capacity();
390 size_t NewCapacity = size_t(
NextPowerOf2(this->capacity() + 2));
391 NewCapacity = std::min(std::max(NewCapacity, MinSize), this->SizeTypeMax());
392 T *NewElts =
static_cast<T *
>(
malloc(NewCapacity *
sizeof(T)));
396 this->uninitialized_move(this->begin(), this->end(), NewElts);
400 destroy_range(this->begin(), this->end());
403 if (!this->isSmall())
407 this->fBeginX = NewElts;
408 this->fCapacity = NewCapacity;
427 template <
typename It1,
typename It2>
431 uninitialized_copy(
I, E, Dest);
436 template <
typename It1,
typename It2>
440 std::uninitialized_copy(
I, E, Dest);
445 template <
typename T1,
typename T2>
448 typename std::enable_if<std::is_same<
typename std::remove_const<T1>::type,
T2>::value>
::type * =
nullptr)
455 memcpy(
reinterpret_cast<void *
>(Dest),
I, (E -
I) *
sizeof(T));
462 this->grow_pod(MinSize,
sizeof(T));
475 memcpy(
reinterpret_cast<void *
>(this->end()), &Elt,
sizeof(T));
476 this->set_size(this->
size() + 1);
484template <
typename T,
unsigned N>
486 alignas(T)
char InlineElts[
N *
sizeof(T)]{};
502#ifdef R__HAS_HARDWARE_INTERFERENCE_SIZE
503 constexpr std::size_t cacheLineSize = std::hardware_destructive_interference_size;
506 static constexpr std::size_t cacheLineSize = 64;
508 static constexpr unsigned elementsPerCacheLine = (cacheLineSize -
sizeof(
SmallVectorBase)) /
sizeof(T);
509 static constexpr unsigned maxInlineByteSize = 1024;
512 static constexpr unsigned value =
513 elementsPerCacheLine >= 8 ? elementsPerCacheLine : (
sizeof(T) * 8 > maxInlineByteSize ? 0 : 8);
536 explicit RVecImpl(
unsigned N) : Internal::VecOps::SmallVectorTemplateBase<T>(
N) {}
545 if (!this->isSmall() && this->Owns())
553 this->destroy_range(this->begin(), this->end());
556 this->resetToSmall();
562 if (N < this->
size()) {
564 this->destroy_range(this->begin() +
N, this->end());
566 }
else if (
N > this->
size()) {
567 if (this->capacity() <
N)
569 for (
auto I = this->end(), E = this->begin() +
N;
I != E; ++
I)
577 if (N < this->
size()) {
579 this->destroy_range(this->begin() +
N, this->end());
581 }
else if (
N > this->
size()) {
582 if (this->capacity() <
N)
584 std::uninitialized_fill(this->end(), this->begin() +
N, NV);
591 if (this->capacity() <
N)
597 if (this->
size() < NumItems) {
598 throw std::runtime_error(
"Popping back more elements than those available.");
601 this->destroy_range(this->end() - NumItems, this->end());
602 this->set_size(this->
size() - NumItems);
607 T Result = ::std::move(this->back());
615 template <
typename in_iter,
616 typename =
typename std::enable_if<std::is_convertible<
617 typename std::iterator_traits<in_iter>::iterator_category, std::input_iterator_tag>::value>
::type>
618 void append(in_iter in_start, in_iter in_end)
620 size_type NumInputs = std::distance(in_start, in_end);
621 if (NumInputs > this->capacity() - this->
size())
622 this->grow(this->
size() + NumInputs);
624 this->uninitialized_copy(in_start, in_end, this->end());
625 this->set_size(this->
size() + NumInputs);
631 if (NumInputs > this->capacity() - this->
size())
632 this->grow(this->
size() + NumInputs);
634 std::uninitialized_fill_n(this->end(), NumInputs, Elt);
635 this->set_size(this->
size() + NumInputs);
638 void append(std::initializer_list<T> IL) {
append(IL.begin(), IL.end()); }
647 if (this->capacity() < NumElts)
649 this->set_size(NumElts);
650 std::uninitialized_fill(this->begin(), this->end(), Elt);
653 template <
typename in_iter,
654 typename =
typename std::enable_if<std::is_convertible<
655 typename std::iterator_traits<in_iter>::iterator_category, std::input_iterator_tag>::value>
::type>
656 void assign(in_iter in_start, in_iter in_end)
659 append(in_start, in_end);
673 if (I < this->begin() ||
I >= this->end()) {
674 throw std::runtime_error(
"The iterator passed to `erase` is out of bounds.");
679 std::move(
I + 1, this->end(),
I);
691 if (S < this->begin() || E > this->end() || S > E) {
692 throw std::runtime_error(
"Invalid start/end pair passed to `erase` (out of bounds or start > end).");
697 iterator I = std::move(E, this->end(), S);
700 this->destroy_range(
I, this->end());
701 this->set_size(
I - this->begin());
707 if (
I == this->end()) {
708 this->push_back(::std::move(Elt));
709 return this->end() - 1;
712 if (I < this->begin() ||
I > this->end()) {
713 throw std::runtime_error(
"The iterator passed to `insert` is out of bounds.");
716 if (this->
size() >= this->capacity()) {
717 size_t EltNo =
I - this->begin();
719 I = this->begin() + EltNo;
722 ::new ((
void *)this->end()) T(::std::move(this->back()));
724 std::move_backward(
I, this->end() - 1, this->end());
725 this->set_size(this->
size() + 1);
730 if (
I <= EltPtr && EltPtr < this->end())
733 *
I = ::std::move(*EltPtr);
739 if (
I == this->end()) {
740 this->push_back(Elt);
741 return this->end() - 1;
744 if (I < this->begin() ||
I > this->end()) {
745 throw std::runtime_error(
"The iterator passed to `insert` is out of bounds.");
748 if (this->
size() >= this->capacity()) {
749 size_t EltNo =
I - this->begin();
751 I = this->begin() + EltNo;
753 ::new ((
void *)this->end()) T(std::move(this->back()));
755 std::move_backward(
I, this->end() - 1, this->end());
756 this->set_size(this->
size() + 1);
760 const T *EltPtr = &Elt;
761 if (
I <= EltPtr && EltPtr < this->end())
771 size_t InsertElt =
I - this->begin();
773 if (
I == this->end()) {
774 append(NumToInsert, Elt);
775 return this->begin() + InsertElt;
778 if (I < this->begin() ||
I > this->end()) {
779 throw std::runtime_error(
"The iterator passed to `insert` is out of bounds.");
783 reserve(this->
size() + NumToInsert);
786 I = this->begin() + InsertElt;
792 if (
size_t(this->end() -
I) >= NumToInsert) {
793 T *OldEnd = this->end();
794 append(std::move_iterator<iterator>(this->end() - NumToInsert), std::move_iterator<iterator>(this->end()));
797 std::move_backward(
I, OldEnd - NumToInsert, OldEnd);
799 std::fill_n(
I, NumToInsert, Elt);
807 T *OldEnd = this->end();
808 this->set_size(this->
size() + NumToInsert);
809 size_t NumOverwritten = OldEnd -
I;
810 this->uninitialized_move(
I, OldEnd, this->end() - NumOverwritten);
813 std::fill_n(
I, NumOverwritten, Elt);
816 std::uninitialized_fill_n(OldEnd, NumToInsert - NumOverwritten, Elt);
820 template <
typename ItTy,
821 typename =
typename std::enable_if<std::is_convertible<
822 typename std::iterator_traits<ItTy>::iterator_category, std::input_iterator_tag>::value>
::type>
826 size_t InsertElt =
I - this->begin();
828 if (
I == this->end()) {
830 return this->begin() + InsertElt;
833 if (I < this->begin() ||
I > this->end()) {
834 throw std::runtime_error(
"The iterator passed to `insert` is out of bounds.");
837 size_t NumToInsert = std::distance(From, To);
840 reserve(this->
size() + NumToInsert);
843 I = this->begin() + InsertElt;
849 if (
size_t(this->end() -
I) >= NumToInsert) {
850 T *OldEnd = this->end();
851 append(std::move_iterator<iterator>(this->end() - NumToInsert), std::move_iterator<iterator>(this->end()));
854 std::move_backward(
I, OldEnd - NumToInsert, OldEnd);
856 std::copy(From, To,
I);
864 T *OldEnd = this->end();
865 this->set_size(this->
size() + NumToInsert);
866 size_t NumOverwritten = OldEnd -
I;
867 this->uninitialized_move(
I, OldEnd, this->end() - NumOverwritten);
870 for (T *J =
I; NumOverwritten > 0; --NumOverwritten) {
877 this->uninitialized_copy(From, To, OldEnd);
883 template <
typename... ArgTypes>
888 return insert(
I, T(std::forward<Args>...));
891 template <
typename... ArgTypes>
896 ::new ((
void *)this->end()) T(std::forward<ArgTypes>(Args)...);
897 this->set_size(this->
size() + 1);
913 if (!this->isSmall() && !RHS.
isSmall()) {
914 std::swap(this->fBeginX, RHS.
fBeginX);
916 std::swap(this->fCapacity, RHS.
fCapacity);
922 if (this->isSmall() && !RHS.
Owns()) {
924 temp = std::move(RHS);
925 RHS = std::move(*
this);
926 *
this = std::move(temp);
928 }
else if (RHS.
isSmall() && !this->Owns()) {
930 temp = std::move(*
this);
931 *
this = std::move(RHS);
932 RHS = std::move(temp);
936 if (RHS.
size() > this->capacity())
937 this->grow(RHS.
size());
942 size_t NumShared = this->
size();
943 if (NumShared > RHS.
size())
944 NumShared = RHS.
size();
945 for (
size_type i = 0; i != NumShared; ++i)
946 std::iter_swap(this->begin() + i, RHS.
begin() + i);
950 size_t EltDiff = this->
size() - RHS.
size();
951 this->uninitialized_copy(this->begin() + NumShared, this->end(), RHS.
end());
954 this->destroy_range(this->begin() + NumShared, this->end());
955 this->set_size(NumShared);
956 }
else if (RHS.
size() > this->size()) {
957 size_t EltDiff = RHS.
size() - this->
size();
958 this->uninitialized_copy(RHS.
begin() + NumShared, RHS.
end(), this->end());
959 this->set_size(this->
size() + EltDiff);
961 this->destroy_range(RHS.
begin() + NumShared, RHS.
end());
975 size_t RHSSize = RHS.
size();
976 size_t CurSize = this->
size();
977 if (CurSize >= RHSSize) {
981 NewEnd = std::copy(RHS.
begin(), RHS.
begin() + RHSSize, this->begin());
983 NewEnd = this->begin();
987 this->destroy_range(NewEnd, this->end());
990 this->set_size(RHSSize);
998 if (this->capacity() < RHSSize) {
1001 this->destroy_range(this->begin(), this->end());
1005 this->grow(RHSSize);
1006 }
else if (CurSize) {
1008 std::copy(RHS.
begin(), RHS.
begin() + CurSize, this->begin());
1012 this->uninitialized_copy(RHS.
begin() + CurSize, RHS.
end(), this->begin() + CurSize);
1015 this->set_size(RHSSize);
1019template <
typename T>
1027 if (!RHS.isSmall()) {
1029 this->destroy_range(this->begin(), this->end());
1030 if (!this->isSmall())
1031 free(this->begin());
1033 this->fBeginX = RHS.fBeginX;
1034 this->
fSize = RHS.fSize;
1035 this->fCapacity = RHS.fCapacity;
1042 size_t RHSSize = RHS.size();
1043 size_t CurSize = this->
size();
1044 if (CurSize >= RHSSize) {
1048 NewEnd = std::move(RHS.begin(), RHS.end(), NewEnd);
1052 this->destroy_range(NewEnd, this->end());
1053 this->set_size(RHSSize);
1066 if (this->capacity() < RHSSize) {
1069 this->destroy_range(this->begin(), this->end());
1073 this->grow(RHSSize);
1074 }
else if (CurSize) {
1076 std::move(RHS.begin(), RHS.begin() + CurSize, this->begin());
1080 this->uninitialized_move(RHS.begin() + CurSize, RHS.end(), this->begin() + CurSize);
1083 this->set_size(RHSSize);
1089template <
typename T>
1095template <
typename T>
1122template <
typename T,
unsigned int N>
1131 this->destroy_range(this->begin(), this->end());
1135 explicit RVecN(
size_t Size,
const T &
Value) : Detail::VecOps::RVecImpl<T>(
N) { this->assign(Size,
Value); }
1137 explicit RVecN(
size_t Size) : Detail::VecOps::RVecImpl<T>(
N)
1142 std::uninitialized_fill(this->begin(), this->end(), T{});
1145 template <
typename ItTy,
1146 typename =
typename std::enable_if<std::is_convertible<
1147 typename std::iterator_traits<ItTy>::iterator_category, std::input_iterator_tag>::value>
::type>
1148 RVecN(ItTy S, ItTy E) : Detail::VecOps::RVecImpl<T>(
N)
1153 RVecN(std::initializer_list<T> IL) : Detail::VecOps::RVecImpl<T>(
N) { this->assign(IL); }
1179 RVecN(
const std::vector<T> &RHS) :
RVecN(RHS.begin(), RHS.end()) {}
1187 RVecN(T* p,
size_t n) : Detail::VecOps::RVecImpl<T>(
N)
1191 this->fCapacity = -1;
1215 return begin()[idx];
1220 return begin()[idx];
1223 template <typename V, unsigned M, typename = std::enable_if<std::is_convertible<V, bool>::value>>
1228 if (
n != this->
size())
1229 throw std::runtime_error(
"Cannot index RVecN with condition vector of different size");
1232 for (
auto c : conds)
1248 template <typename U, unsigned M, typename = std::enable_if<std::is_convertible<T, U>::value>>
1257 throw std::out_of_range(
"RVecN");
1258 return this->operator[](pos);
1264 throw std::out_of_range(
"RVecN");
1265 return this->operator[](pos);
1273 return this->operator[](pos);
1281 return this->operator[](pos);
1454template <
typename T>
1455class R__CLING_PTRCHECK(off)
RVec :
public RVecN<T, Internal::VecOps::RVecInlineStorageSize<T>::value> {
1462 using SuperClass::begin;
1463 using SuperClass::size;
1471 template <
typename ItTy,
1472 typename =
typename std::enable_if<std::is_convertible<
1473 typename std::iterator_traits<ItTy>::iterator_category, std::input_iterator_tag>::value>
::type>
1484 SuperClass::operator=(RHS);
1492 SuperClass::operator=(std::move(RHS));
1498 template <
unsigned N>
1501 template <
unsigned N>
1509 template <typename U, typename = std::enable_if<std::is_convertible<T, U>::value>>
1512 return RVec<U>(this->begin(), this->end());
1515 using SuperClass::operator[];
1517 template <typename V, typename = std::enable_if<std::is_convertible<V, bool>::value>>
1520 return RVec(SuperClass::operator[](conds));
1523 using SuperClass::at;
1525 friend bool ROOT::Detail::VecOps::IsSmall<T>(
const RVec<T> &
v);
1527 friend bool ROOT::Detail::VecOps::IsAdopting<T>(
const RVec<T> &
v);
1530template <
typename T,
unsigned N>
1539#define RVEC_UNARY_OPERATOR(OP) \
1540template <typename T> \
1541RVec<T> operator OP(const RVec<T> &v) \
1544 for (auto &x : ret) \
1553#undef RVEC_UNARY_OPERATOR
1559#define ERROR_MESSAGE(OP) \
1560 "Cannot call operator " #OP " on vectors of different sizes."
1562#define RVEC_BINARY_OPERATOR(OP) \
1563template <typename T0, typename T1> \
1564auto operator OP(const RVec<T0> &v, const T1 &y) \
1565 -> RVec<decltype(v[0] OP y)> \
1567 RVec<decltype(v[0] OP y)> ret(v.size()); \
1568 auto op = [&y](const T0 &x) { return x OP y; }; \
1569 std::transform(v.begin(), v.end(), ret.begin(), op); \
1573template <typename T0, typename T1> \
1574auto operator OP(const T0 &x, const RVec<T1> &v) \
1575 -> RVec<decltype(x OP v[0])> \
1577 RVec<decltype(x OP v[0])> ret(v.size()); \
1578 auto op = [&x](const T1 &y) { return x OP y; }; \
1579 std::transform(v.begin(), v.end(), ret.begin(), op); \
1583template <typename T0, typename T1> \
1584auto operator OP(const RVec<T0> &v0, const RVec<T1> &v1) \
1585 -> RVec<decltype(v0[0] OP v1[0])> \
1587 if (v0.size() != v1.size()) \
1588 throw std::runtime_error(ERROR_MESSAGE(OP)); \
1590 RVec<decltype(v0[0] OP v1[0])> ret(v0.size()); \
1591 auto op = [](const T0 &x, const T1 &y) { return x OP y; }; \
1592 std::transform(v0.begin(), v0.end(), v1.begin(), ret.begin(), op); \
1604#undef RVEC_BINARY_OPERATOR
1610#define RVEC_ASSIGNMENT_OPERATOR(OP) \
1611template <typename T0, typename T1> \
1612RVec<T0>& operator OP(RVec<T0> &v, const T1 &y) \
1614 auto op = [&y](T0 &x) { return x OP y; }; \
1615 std::transform(v.begin(), v.end(), v.begin(), op); \
1619template <typename T0, typename T1> \
1620RVec<T0>& operator OP(RVec<T0> &v0, const RVec<T1> &v1) \
1622 if (v0.size() != v1.size()) \
1623 throw std::runtime_error(ERROR_MESSAGE(OP)); \
1625 auto op = [](T0 &x, const T1 &y) { return x OP y; }; \
1626 std::transform(v0.begin(), v0.end(), v1.begin(), v0.begin(), op); \
1640#undef RVEC_ASSIGNMENT_OPERATOR
1646#define RVEC_LOGICAL_OPERATOR(OP) \
1647template <typename T0, typename T1> \
1648auto operator OP(const RVec<T0> &v, const T1 &y) \
1651 RVec<int> ret(v.size()); \
1652 auto op = [y](const T0 &x) -> int { return x OP y; }; \
1653 std::transform(v.begin(), v.end(), ret.begin(), op); \
1657template <typename T0, typename T1> \
1658auto operator OP(const T0 &x, const RVec<T1> &v) \
1661 RVec<int> ret(v.size()); \
1662 auto op = [x](const T1 &y) -> int { return x OP y; }; \
1663 std::transform(v.begin(), v.end(), ret.begin(), op); \
1667template <typename T0, typename T1> \
1668auto operator OP(const RVec<T0> &v0, const RVec<T1> &v1) \
1671 if (v0.size() != v1.size()) \
1672 throw std::runtime_error(ERROR_MESSAGE(OP)); \
1674 RVec<int> ret(v0.size()); \
1675 auto op = [](const T0 &x, const T1 &y) -> int { return x OP y; }; \
1676 std::transform(v0.begin(), v0.end(), v1.begin(), ret.begin(), op); \
1688#undef RVEC_LOGICAL_OPERATOR
1695template <
typename T>
struct PromoteTypeImpl;
1697template <>
struct PromoteTypeImpl<float> {
using Type = float; };
1701template <
typename T>
struct PromoteTypeImpl {
using Type =
double; };
1703template <
typename T>
1704using PromoteType =
typename PromoteTypeImpl<T>::Type;
1706template <
typename U,
typename V>
1707using PromoteTypes =
decltype(PromoteType<U>() + PromoteType<V>());
1711#define RVEC_UNARY_FUNCTION(NAME, FUNC) \
1712 template <typename T> \
1713 RVec<PromoteType<T>> NAME(const RVec<T> &v) \
1715 RVec<PromoteType<T>> ret(v.size()); \
1716 auto f = [](const T &x) { return FUNC(x); }; \
1717 std::transform(v.begin(), v.end(), ret.begin(), f); \
1721#define RVEC_BINARY_FUNCTION(NAME, FUNC) \
1722 template <typename T0, typename T1> \
1723 RVec<PromoteTypes<T0, T1>> NAME(const T0 &x, const RVec<T1> &v) \
1725 RVec<PromoteTypes<T0, T1>> ret(v.size()); \
1726 auto f = [&x](const T1 &y) { return FUNC(x, y); }; \
1727 std::transform(v.begin(), v.end(), ret.begin(), f); \
1731 template <typename T0, typename T1> \
1732 RVec<PromoteTypes<T0, T1>> NAME(const RVec<T0> &v, const T1 &y) \
1734 RVec<PromoteTypes<T0, T1>> ret(v.size()); \
1735 auto f = [&y](const T1 &x) { return FUNC(x, y); }; \
1736 std::transform(v.begin(), v.end(), ret.begin(), f); \
1740 template <typename T0, typename T1> \
1741 RVec<PromoteTypes<T0, T1>> NAME(const RVec<T0> &v0, const RVec<T1> &v1) \
1743 if (v0.size() != v1.size()) \
1744 throw std::runtime_error(ERROR_MESSAGE(NAME)); \
1746 RVec<PromoteTypes<T0, T1>> ret(v0.size()); \
1747 auto f = [](const T0 &x, const T1 &y) { return FUNC(x, y); }; \
1748 std::transform(v0.begin(), v0.end(), v1.begin(), ret.begin(), f); \
1752#define RVEC_STD_UNARY_FUNCTION(F) RVEC_UNARY_FUNCTION(F, std::F)
1753#define RVEC_STD_BINARY_FUNCTION(F) RVEC_BINARY_FUNCTION(F, std::F)
1800#undef RVEC_STD_UNARY_FUNCTION
1807#define RVEC_VDT_UNARY_FUNCTION(F) RVEC_UNARY_FUNCTION(F, vdt::F)
1809RVEC_VDT_UNARY_FUNCTION(fast_expf)
1810RVEC_VDT_UNARY_FUNCTION(fast_logf)
1811RVEC_VDT_UNARY_FUNCTION(fast_sinf)
1812RVEC_VDT_UNARY_FUNCTION(fast_cosf)
1813RVEC_VDT_UNARY_FUNCTION(fast_tanf)
1814RVEC_VDT_UNARY_FUNCTION(fast_asinf)
1815RVEC_VDT_UNARY_FUNCTION(fast_acosf)
1816RVEC_VDT_UNARY_FUNCTION(fast_atanf)
1818RVEC_VDT_UNARY_FUNCTION(fast_exp)
1819RVEC_VDT_UNARY_FUNCTION(fast_log)
1820RVEC_VDT_UNARY_FUNCTION(fast_sin)
1821RVEC_VDT_UNARY_FUNCTION(fast_cos)
1822RVEC_VDT_UNARY_FUNCTION(fast_tan)
1823RVEC_VDT_UNARY_FUNCTION(fast_asin)
1824RVEC_VDT_UNARY_FUNCTION(fast_acos)
1825RVEC_VDT_UNARY_FUNCTION(fast_atan)
1826#undef RVEC_VDT_UNARY_FUNCTION
1830#undef RVEC_UNARY_FUNCTION
1845template <
typename T,
typename V>
1848 if (
v0.size() !=
v1.size())
1849 throw std::runtime_error(
"Cannot compute inner product of vectors of different sizes");
1850 return std::inner_product(
v0.begin(),
v0.end(),
v1.begin(),
decltype(
v0[0] *
v1[0])(0));
1876template <
typename T,
typename R = T>
1879 return std::accumulate(
v.begin(),
v.end(), zero);
1894template <
typename T>
1897 if (
v.empty())
return 0.;
1926template <
typename T,
typename R = T>
1929 if (
v.empty())
return zero;
1930 return Sum(
v, zero) /
v.size();
1943template <
typename T>
1946 return *std::max_element(
v.begin(),
v.end());
1959template <
typename T>
1962 return *std::min_element(
v.begin(),
v.end());
1977template <
typename T>
1980 return std::distance(
v.begin(), std::max_element(
v.begin(),
v.end()));
1995template <
typename T>
1998 return std::distance(
v.begin(), std::min_element(
v.begin(),
v.end()));
2012template <
typename T>
2015 const std::size_t
size =
v.size();
2016 if (
size < std::size_t(2))
return 0.;
2017 T sum_squares(0), squared_sum(0);
2018 auto pred = [&sum_squares, &squared_sum](
const T&
x) {sum_squares+=
x*
x; squared_sum+=
x;};
2019 std::for_each(
v.begin(),
v.end(), pred);
2020 squared_sum *= squared_sum;
2022 return 1. / (dsize - 1.) * (sum_squares - squared_sum / dsize );
2036template <
typename T>
2039 return std::sqrt(
Var(
v));
2060template <
typename... Args>
2072 std::make_index_sequence<
sizeof...(args) - 1>());
2085template <
typename T,
typename F>
2088 const auto thisSize =
v.size();
2091 for (
auto &&val :
v) {
2108template <
typename T>
2127template <
typename T>
2136template <
typename T>
2153template <
typename T>
2159 std::sort(i.
begin(), i.
end(), [&
v](size_type i1, size_type i2) { return v[i1] < v[i2]; });
2174template <
typename T,
typename Compare>
2181 [&
v, &
c](size_type i1, size_type i2) { return c(v[i1], v[i2]); });
2198template <
typename T>
2204 std::stable_sort(i.
begin(), i.
end(), [&
v](size_type i1, size_type i2) { return v[i1] < v[i2]; });
2221template <
typename T,
typename Compare>
2227 std::stable_sort(i.
begin(), i.
end(), [&
v, &
c](size_type i1, size_type i2) { return c(v[i1], v[i2]); });
2241template <
typename T>
2245 const size_type isize = i.size();
2247 for (size_type k = 0; k < isize; k++)
2267template <
typename T>
2271 const size_type
size =
v.size();
2272 const size_type absn = std::abs(
n);
2274 std::stringstream ss;
2275 ss <<
"Try to take " << absn <<
" elements but vector has only size " <<
size <<
".";
2276 throw std::runtime_error(ss.str());
2280 for (size_type k = 0; k < absn; k++)
2281 r[k] =
v[
size - absn + k];
2283 for (size_type k = 0; k < absn; k++)
2292template <
typename T>
2296 std::sort(idxs.begin(), idxs.end());
2297 idxs.erase(std::unique(idxs.begin(), idxs.end()), idxs.end());
2300 if (
v.size() > idxs.size())
2301 r.reserve(
v.size() - idxs.size());
2303 auto discardIt = idxs.begin();
2305 for (sz_t i = 0u; i <
v.size(); ++i) {
2306 if (discardIt != idxs.end() && i == *discardIt)
2309 r.emplace_back(
v[i]);
2325template <
typename T>
2329 std::reverse(
r.begin(),
r.end());
2346template <
typename T>
2350 std::sort(
r.begin(),
r.end());
2371template <
typename T,
typename Compare>
2375 std::sort(
r.begin(),
r.end(), std::forward<Compare>(
c));
2395template <
typename T>
2399 std::stable_sort(
r.begin(),
r.end());
2431template <
typename T,
typename Compare>
2435 std::stable_sort(
r.begin(),
r.end(), std::forward<Compare>(
c));
2453 using size_type = std::size_t;
2455 r[0].resize(size1*size2);
2456 r[1].resize(size1*size2);
2458 for(size_type i=0; i<size1; i++) {
2459 for(size_type j=0; j<size2; j++) {
2482template <
typename T1,
typename T2>
2507template <
typename T>
2511 const size_type s =
v.size();
2513 throw std::runtime_error(
"Cannot make unique combinations of size " + std::to_string(
n) +
2514 " from vector of size " + std::to_string(s) +
".");
2518 for(size_type k=0; k<s; k++)
2521 const auto innersize = [=] {
2522 size_type inners = s -
n + 1;
2523 for (size_type
m = s -
n + 2;
m <= s; ++
m)
2526 size_type factn = 1;
2527 for (size_type i = 2; i <=
n; ++i)
2535 size_type inneridx = 0;
2536 for (size_type k = 0; k <
n; k++)
2541 bool run_through =
true;
2545 run_through =
false;
2553 for (
long j=i+1; j<(
long)
n; j++)
2555 for (size_type k = 0; k <
n; k++)
2571template <
typename T>
2576 const auto size =
v.size();
2578 for(size_type i=0; i<
size; i++) {
2602template <
typename T>
2606 if (!v2_is_sorted) v2_sorted = Sort(
v2);
2607 const auto v2_begin = v2_is_sorted ?
v2.begin() : v2_sorted.
begin();
2608 const auto v2_end = v2_is_sorted ?
v2.end() : v2_sorted.
end();
2610 const auto size =
v1.size();
2613 for(size_type i=0; i<
size; i++) {
2614 if (std::binary_search(v2_begin, v2_end,
v1[i])) {
2615 r.emplace_back(
v1[i]);
2636template <
typename T>
2640 const size_type
size =
c.size();
2643 for (size_type i=0; i<
size; i++) {
2644 r.emplace_back(
c[i] != 0 ?
v1[i] :
v2[i]);
2664template <
typename T>
2668 const size_type
size =
c.size();
2671 for (size_type i=0; i<
size; i++) {
2672 r.emplace_back(
c[i] != 0 ?
v1[i] :
v2);
2692template <
typename T>
2696 const size_type
size =
c.size();
2699 for (size_type i=0; i<
size; i++) {
2700 r.emplace_back(
c[i] != 0 ?
v1 :
v2[i]);
2718template <
typename T>
2722 const size_type
size =
c.size();
2725 for (size_type i=0; i<
size; i++) {
2726 r.emplace_back(
c[i] != 0 ?
v1 :
v2);
2741template <typename T0, typename T1, typename Common_t = typename std::common_type<T0, T1>::type>
2746 std::copy(
v0.begin(),
v0.end(), std::back_inserter(res));
2747 std::copy(
v1.begin(),
v1.end(), std::back_inserter(res));
2757template <
typename T>
2760 static_assert(std::is_floating_point<T>::value,
2761 "DeltaPhi must be called with floating point values.");
2762 auto r = std::fmod(
v2 -
v1, 2.0 *
c);
2778template <
typename T>
2782 const size_type
size =
v1.size();
2784 for (size_type i = 0; i <
size; i++) {
2785 r[i] = DeltaPhi(
v1[i],
v2[i],
c);
2796template <
typename T>
2800 const size_type
size =
v1.size();
2802 for (size_type i = 0; i <
size; i++) {
2803 r[i] = DeltaPhi(
v1[i],
v2,
c);
2814template <
typename T>
2818 const size_type
size =
v2.size();
2820 for (size_type i = 0; i <
size; i++) {
2821 r[i] = DeltaPhi(
v1,
v2[i],
c);
2833template <
typename T>
2836 const auto dphi = DeltaPhi(phi1, phi2,
c);
2837 return (eta1 - eta2) * (eta1 - eta2) + dphi * dphi;
2847template <
typename T>
2850 return sqrt(DeltaR2(eta1, eta2, phi1, phi2,
c));
2860template <
typename T>
2861T DeltaR(T eta1, T eta2, T phi1, T phi2,
const T
c =
M_PI)
2863 const auto dphi = DeltaPhi(phi1, phi2,
c);
2864 return std::sqrt((eta1 - eta2) * (eta1 - eta2) + dphi * dphi);
2872template <
typename T>
2884 for (std::size_t i = 0u; i <
size; ++i) {
2886 const auto x1 = pt1[i] * std::cos(phi1[i]);
2887 const auto y1 = pt1[i] * std::sin(phi1[i]);
2888 const auto z1 = pt1[i] * std::sinh(eta1[i]);
2889 const auto e1 = std::sqrt(
x1 *
x1 + y1 * y1 + z1 * z1 + mass1[i] * mass1[i]);
2891 const auto x2 = pt2[i] * std::cos(phi2[i]);
2892 const auto y2 = pt2[i] * std::sin(phi2[i]);
2893 const auto z2 = pt2[i] * std::sinh(eta2[i]);
2894 const auto e2 = std::sqrt(
x2 *
x2 + y2 * y2 + z2 * z2 + mass2[i] * mass2[i]);
2897 const auto e = e1 + e2;
2898 const auto x =
x1 +
x2;
2899 const auto y = y1 + y2;
2900 const auto z = z1 + z2;
2902 inv_masses[i] = std::sqrt(
e *
e -
x *
x -
y *
y - z * z);
2914template <
typename T>
2917 const std::size_t
size =
pt.size();
2926 for (std::size_t i = 0u; i <
size; ++ i) {
2928 const auto x =
pt[i] * std::cos(phi[i]);
2930 const auto y =
pt[i] * std::sin(phi[i]);
2932 const auto z =
pt[i] * std::sinh(eta[i]);
2934 const auto e = std::sqrt(
x *
x +
y *
y + z * z + mass[i] * mass[i]);
2939 return std::sqrt(e_sum * e_sum - x_sum * x_sum - y_sum * y_sum - z_sum * z_sum);
2960template <
typename T,
typename... Args_t>
2966 for (
auto i = 0UL; i <
size; ++i) {
2978 constexpr bool mustConvert = std::is_same<char, T>::value || std::is_same<signed char, T>::value ||
2979 std::is_same<unsigned char, T>::value || std::is_same<wchar_t, T>::value ||
2980 std::is_same<char16_t, T>::value || std::is_same<char32_t, T>::value;
2981 using Print_t =
typename std::conditional<mustConvert, long long int, T>::type;
2983 auto size =
v.size();
2985 for (std::size_t i = 0; i <
size - 1; ++i) {
2986 os << (Print_t)
v[i] <<
", ";
2988 os << (Print_t)
v[
size - 1];
2994#if (_VECOPS_USE_EXTERN_TEMPLATES)
2996#define RVEC_EXTERN_UNARY_OPERATOR(T, OP) \
2997 extern template RVec<T> operator OP<T>(const RVec<T> &);
2999#define RVEC_EXTERN_BINARY_OPERATOR(T, OP) \
3000 extern template auto operator OP<T, T>(const T &x, const RVec<T> &v) \
3001 -> RVec<decltype(x OP v[0])>; \
3002 extern template auto operator OP<T, T>(const RVec<T> &v, const T &y) \
3003 -> RVec<decltype(v[0] OP y)>; \
3004 extern template auto operator OP<T, T>(const RVec<T> &v0, const RVec<T> &v1)\
3005 -> RVec<decltype(v0[0] OP v1[0])>;
3007#define RVEC_EXTERN_ASSIGN_OPERATOR(T, OP) \
3008 extern template RVec<T> &operator OP<T, T>(RVec<T> &, const T &); \
3009 extern template RVec<T> &operator OP<T, T>(RVec<T> &, const RVec<T> &);
3011#define RVEC_EXTERN_LOGICAL_OPERATOR(T, OP) \
3012 extern template RVec<int> operator OP<T, T>(const RVec<T> &, const T &); \
3013 extern template RVec<int> operator OP<T, T>(const T &, const RVec<T> &); \
3014 extern template RVec<int> operator OP<T, T>(const RVec<T> &, const RVec<T> &);
3016#define RVEC_EXTERN_FLOAT_TEMPLATE(T) \
3017 extern template class RVec<T>; \
3018 RVEC_EXTERN_UNARY_OPERATOR(T, +) \
3019 RVEC_EXTERN_UNARY_OPERATOR(T, -) \
3020 RVEC_EXTERN_UNARY_OPERATOR(T, !) \
3021 RVEC_EXTERN_BINARY_OPERATOR(T, +) \
3022 RVEC_EXTERN_BINARY_OPERATOR(T, -) \
3023 RVEC_EXTERN_BINARY_OPERATOR(T, *) \
3024 RVEC_EXTERN_BINARY_OPERATOR(T, /) \
3025 RVEC_EXTERN_ASSIGN_OPERATOR(T, +=) \
3026 RVEC_EXTERN_ASSIGN_OPERATOR(T, -=) \
3027 RVEC_EXTERN_ASSIGN_OPERATOR(T, *=) \
3028 RVEC_EXTERN_ASSIGN_OPERATOR(T, /=) \
3029 RVEC_EXTERN_LOGICAL_OPERATOR(T, <) \
3030 RVEC_EXTERN_LOGICAL_OPERATOR(T, >) \
3031 RVEC_EXTERN_LOGICAL_OPERATOR(T, ==) \
3032 RVEC_EXTERN_LOGICAL_OPERATOR(T, !=) \
3033 RVEC_EXTERN_LOGICAL_OPERATOR(T, <=) \
3034 RVEC_EXTERN_LOGICAL_OPERATOR(T, >=) \
3035 RVEC_EXTERN_LOGICAL_OPERATOR(T, &&) \
3036 RVEC_EXTERN_LOGICAL_OPERATOR(T, ||)
3038#define RVEC_EXTERN_INTEGER_TEMPLATE(T) \
3039 extern template class RVec<T>; \
3040 RVEC_EXTERN_UNARY_OPERATOR(T, +) \
3041 RVEC_EXTERN_UNARY_OPERATOR(T, -) \
3042 RVEC_EXTERN_UNARY_OPERATOR(T, ~) \
3043 RVEC_EXTERN_UNARY_OPERATOR(T, !) \
3044 RVEC_EXTERN_BINARY_OPERATOR(T, +) \
3045 RVEC_EXTERN_BINARY_OPERATOR(T, -) \
3046 RVEC_EXTERN_BINARY_OPERATOR(T, *) \
3047 RVEC_EXTERN_BINARY_OPERATOR(T, /) \
3048 RVEC_EXTERN_BINARY_OPERATOR(T, %) \
3049 RVEC_EXTERN_BINARY_OPERATOR(T, &) \
3050 RVEC_EXTERN_BINARY_OPERATOR(T, |) \
3051 RVEC_EXTERN_BINARY_OPERATOR(T, ^) \
3052 RVEC_EXTERN_ASSIGN_OPERATOR(T, +=) \
3053 RVEC_EXTERN_ASSIGN_OPERATOR(T, -=) \
3054 RVEC_EXTERN_ASSIGN_OPERATOR(T, *=) \
3055 RVEC_EXTERN_ASSIGN_OPERATOR(T, /=) \
3056 RVEC_EXTERN_ASSIGN_OPERATOR(T, %=) \
3057 RVEC_EXTERN_ASSIGN_OPERATOR(T, &=) \
3058 RVEC_EXTERN_ASSIGN_OPERATOR(T, |=) \
3059 RVEC_EXTERN_ASSIGN_OPERATOR(T, ^=) \
3060 RVEC_EXTERN_ASSIGN_OPERATOR(T, >>=) \
3061 RVEC_EXTERN_ASSIGN_OPERATOR(T, <<=) \
3062 RVEC_EXTERN_LOGICAL_OPERATOR(T, <) \
3063 RVEC_EXTERN_LOGICAL_OPERATOR(T, >) \
3064 RVEC_EXTERN_LOGICAL_OPERATOR(T, ==) \
3065 RVEC_EXTERN_LOGICAL_OPERATOR(T, !=) \
3066 RVEC_EXTERN_LOGICAL_OPERATOR(T, <=) \
3067 RVEC_EXTERN_LOGICAL_OPERATOR(T, >=) \
3068 RVEC_EXTERN_LOGICAL_OPERATOR(T, &&) \
3069 RVEC_EXTERN_LOGICAL_OPERATOR(T, ||)
3071RVEC_EXTERN_INTEGER_TEMPLATE(
char)
3072RVEC_EXTERN_INTEGER_TEMPLATE(
short)
3073RVEC_EXTERN_INTEGER_TEMPLATE(
int)
3074RVEC_EXTERN_INTEGER_TEMPLATE(
long)
3077RVEC_EXTERN_INTEGER_TEMPLATE(
unsigned char)
3078RVEC_EXTERN_INTEGER_TEMPLATE(
unsigned short)
3079RVEC_EXTERN_INTEGER_TEMPLATE(
unsigned int)
3080RVEC_EXTERN_INTEGER_TEMPLATE(
unsigned long)
3083RVEC_EXTERN_FLOAT_TEMPLATE(
float)
3084RVEC_EXTERN_FLOAT_TEMPLATE(
double)
3086#undef RVEC_EXTERN_UNARY_OPERATOR
3087#undef RVEC_EXTERN_BINARY_OPERATOR
3088#undef RVEC_EXTERN_ASSIGN_OPERATOR
3089#undef RVEC_EXTERN_LOGICAL_OPERATOR
3090#undef RVEC_EXTERN_INTEGER_TEMPLATE
3091#undef RVEC_EXTERN_FLOAT_TEMPLATE
3093#define RVEC_EXTERN_UNARY_FUNCTION(T, NAME, FUNC) \
3094 extern template RVec<PromoteType<T>> NAME(const RVec<T> &);
3096#define RVEC_EXTERN_STD_UNARY_FUNCTION(T, F) RVEC_EXTERN_UNARY_FUNCTION(T, F, std::F)
3098#define RVEC_EXTERN_BINARY_FUNCTION(T0, T1, NAME, FUNC) \
3099 extern template RVec<PromoteTypes<T0, T1>> NAME(const RVec<T0> &, const T1 &); \
3100 extern template RVec<PromoteTypes<T0, T1>> NAME(const T0 &, const RVec<T1> &); \
3101 extern template RVec<PromoteTypes<T0, T1>> NAME(const RVec<T0> &, const RVec<T1> &);
3103#define RVEC_EXTERN_STD_BINARY_FUNCTION(T, F) RVEC_EXTERN_BINARY_FUNCTION(T, T, F, std::F)
3105#define RVEC_EXTERN_STD_FUNCTIONS(T) \
3106 RVEC_EXTERN_STD_UNARY_FUNCTION(T, abs) \
3107 RVEC_EXTERN_STD_BINARY_FUNCTION(T, fdim) \
3108 RVEC_EXTERN_STD_BINARY_FUNCTION(T, fmod) \
3109 RVEC_EXTERN_STD_BINARY_FUNCTION(T, remainder) \
3110 RVEC_EXTERN_STD_UNARY_FUNCTION(T, exp) \
3111 RVEC_EXTERN_STD_UNARY_FUNCTION(T, exp2) \
3112 RVEC_EXTERN_STD_UNARY_FUNCTION(T, expm1) \
3113 RVEC_EXTERN_STD_UNARY_FUNCTION(T, log) \
3114 RVEC_EXTERN_STD_UNARY_FUNCTION(T, log10) \
3115 RVEC_EXTERN_STD_UNARY_FUNCTION(T, log2) \
3116 RVEC_EXTERN_STD_UNARY_FUNCTION(T, log1p) \
3117 RVEC_EXTERN_STD_BINARY_FUNCTION(T, pow) \
3118 RVEC_EXTERN_STD_UNARY_FUNCTION(T, sqrt) \
3119 RVEC_EXTERN_STD_UNARY_FUNCTION(T, cbrt) \
3120 RVEC_EXTERN_STD_BINARY_FUNCTION(T, hypot) \
3121 RVEC_EXTERN_STD_UNARY_FUNCTION(T, sin) \
3122 RVEC_EXTERN_STD_UNARY_FUNCTION(T, cos) \
3123 RVEC_EXTERN_STD_UNARY_FUNCTION(T, tan) \
3124 RVEC_EXTERN_STD_UNARY_FUNCTION(T, asin) \
3125 RVEC_EXTERN_STD_UNARY_FUNCTION(T, acos) \
3126 RVEC_EXTERN_STD_UNARY_FUNCTION(T, atan) \
3127 RVEC_EXTERN_STD_BINARY_FUNCTION(T, atan2) \
3128 RVEC_EXTERN_STD_UNARY_FUNCTION(T, sinh) \
3129 RVEC_EXTERN_STD_UNARY_FUNCTION(T, cosh) \
3130 RVEC_EXTERN_STD_UNARY_FUNCTION(T, tanh) \
3131 RVEC_EXTERN_STD_UNARY_FUNCTION(T, asinh) \
3132 RVEC_EXTERN_STD_UNARY_FUNCTION(T, acosh) \
3133 RVEC_EXTERN_STD_UNARY_FUNCTION(T, atanh) \
3134 RVEC_EXTERN_STD_UNARY_FUNCTION(T, floor) \
3135 RVEC_EXTERN_STD_UNARY_FUNCTION(T, ceil) \
3136 RVEC_EXTERN_STD_UNARY_FUNCTION(T, trunc) \
3137 RVEC_EXTERN_STD_UNARY_FUNCTION(T, round) \
3138 RVEC_EXTERN_STD_UNARY_FUNCTION(T, erf) \
3139 RVEC_EXTERN_STD_UNARY_FUNCTION(T, erfc) \
3140 RVEC_EXTERN_STD_UNARY_FUNCTION(T, lgamma) \
3141 RVEC_EXTERN_STD_UNARY_FUNCTION(T, tgamma) \
3143RVEC_EXTERN_STD_FUNCTIONS(
float)
3144RVEC_EXTERN_STD_FUNCTIONS(
double)
3145#undef RVEC_EXTERN_STD_UNARY_FUNCTION
3146#undef RVEC_EXTERN_STD_BINARY_FUNCTION
3147#undef RVEC_EXTERN_STD_UNARY_FUNCTIONS
3151#define RVEC_EXTERN_VDT_UNARY_FUNCTION(T, F) RVEC_EXTERN_UNARY_FUNCTION(T, F, vdt::F)
3153RVEC_EXTERN_VDT_UNARY_FUNCTION(
float, fast_expf)
3154RVEC_EXTERN_VDT_UNARY_FUNCTION(
float, fast_logf)
3155RVEC_EXTERN_VDT_UNARY_FUNCTION(
float, fast_sinf)
3156RVEC_EXTERN_VDT_UNARY_FUNCTION(
float, fast_cosf)
3157RVEC_EXTERN_VDT_UNARY_FUNCTION(
float, fast_tanf)
3158RVEC_EXTERN_VDT_UNARY_FUNCTION(
float, fast_asinf)
3159RVEC_EXTERN_VDT_UNARY_FUNCTION(
float, fast_acosf)
3160RVEC_EXTERN_VDT_UNARY_FUNCTION(
float, fast_atanf)
3162RVEC_EXTERN_VDT_UNARY_FUNCTION(
double, fast_exp)
3163RVEC_EXTERN_VDT_UNARY_FUNCTION(
double, fast_log)
3164RVEC_EXTERN_VDT_UNARY_FUNCTION(
double, fast_sin)
3165RVEC_EXTERN_VDT_UNARY_FUNCTION(
double, fast_cos)
3166RVEC_EXTERN_VDT_UNARY_FUNCTION(
double, fast_tan)
3167RVEC_EXTERN_VDT_UNARY_FUNCTION(
double, fast_asin)
3168RVEC_EXTERN_VDT_UNARY_FUNCTION(
double, fast_acos)
3169RVEC_EXTERN_VDT_UNARY_FUNCTION(
double, fast_atan)
#define R__unlikely(expr)
#define R__DEPRECATED(MAJOR, MINOR, REASON)
#define R(a, b, c, d, e, f, g, h, i)
#define R__RVEC_NODISCARD
static const double x2[5]
static const double x1[5]
size_t size(const MatrixT &matrix)
retrieve the size of a square matrix
TBuffer & operator<<(TBuffer &buf, const Tmpl *obj)
#define R__CLING_PTRCHECK(ONOFF)
Int_t Compare(const void *item1, const void *item2)
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
void assign(size_type NumElts, const T &Elt)
typename SuperClass::iterator iterator
typename SuperClass::size_type size_type
void append(in_iter in_start, in_iter in_end)
Add the specified range to the end of the SmallVector.
iterator insert(iterator I, T &&Elt)
void assign(std::initializer_list< T > IL)
typename SuperClass::const_iterator const_iterator
void resize(size_type N, const T &NV)
void reserve(size_type N)
iterator insert(iterator I, ItTy From, ItTy To)
reference emplace_back(ArgTypes &&...Args)
void assign(in_iter in_start, in_iter in_end)
iterator insert(iterator I, const T &Elt)
iterator insert(iterator I, size_type NumToInsert, const T &Elt)
RVecImpl & operator=(const RVecImpl &RHS)
iterator erase(const_iterator CS, const_iterator CE)
typename SuperClass::reference reference
void append(size_type NumInputs, const T &Elt)
Append NumInputs copies of Elt to the end.
iterator erase(const_iterator CI)
RVecImpl & operator=(RVecImpl &&RHS)
void pop_back_n(size_type NumItems)
R__RVEC_NODISCARD T pop_back_val()
RVecImpl(const RVecImpl &)=delete
void append(std::initializer_list< T > IL)
void insert(iterator I, std::initializer_list< T > IL)
This is all the stuff common to all SmallVectors.
SmallVectorBase(void *FirstEl, size_t TotalCapacity)
static constexpr size_t SizeTypeMax()
The maximum value of the Size_T used.
Size_T fCapacity
Always >= -1. fCapacity == -1 indicates the RVec is in "memory adoption" mode.
R__RVEC_NODISCARD bool empty() const
bool Owns() const
If true, the RVec is in "memory adoption" mode, i.e. it is acting as a view on a memory buffer it doe...
size_t capacity() const noexcept
void set_size(size_t N)
Set the array size to N, which the current array must have enough capacity for.
typename SuperClass::iterator iterator
void grow(size_t MinSize=0)
Double the size of the allocated memory, guaranteeing space for at least one more element or MinSize ...
typename SuperClass::size_type size_type
typename SuperClass::reference reference
void push_back(const T &Elt)
static void uninitialized_move(It1 I, It1 E, It2 Dest)
Move the range [I, E) onto the uninitialized memory starting with "Dest", constructing elements into ...
SmallVectorTemplateBase(size_t Size)
typename SuperClass::const_iterator const_iterator
static void uninitialized_copy(T1 *I, T1 *E, T2 *Dest, typename std::enable_if< std::is_same< typename std::remove_const< T1 >::type, T2 >::value >::type *=nullptr)
Copy the range [I, E) onto the uninitialized memory starting with "Dest", constructing elements into ...
static void destroy_range(T *, T *)
static void uninitialized_copy(It1 I, It1 E, It2 Dest)
Copy the range [I, E) onto the uninitialized memory starting with "Dest", constructing elements into ...
SmallVectorTemplateBase<TriviallyCopyable = false> - This is where we put method implementations that...
void push_back(const T &Elt)
void grow(size_t MinSize=0)
Grow the allocated memory (without initializing new elements), doubling the size of the allocated mem...
static void uninitialized_move(It1 I, It1 E, It2 Dest)
Move the range [I, E) into the uninitialized memory starting with "Dest", constructing elements as ne...
SmallVectorTemplateBase(size_t Size)
static void destroy_range(T *S, T *E)
static void uninitialized_copy(It1 I, It1 E, It2 Dest)
Copy the range [I, E) onto the uninitialized memory starting with "Dest", constructing elements as ne...
This is the part of SmallVectorTemplateBase which does not depend on whether the type T is a POD.
size_type max_size() const noexcept
const_iterator cbegin() const noexcept
void grow_pod(size_t MinSize, size_t TSize)
ptrdiff_t difference_type
reverse_iterator rbegin() noexcept
const_iterator cend() const noexcept
const_reference back() const
void resetToSmall()
Put this vector in a state of being small.
iterator begin() noexcept
std::reverse_iterator< iterator > reverse_iterator
const T & const_reference
bool isSmall() const
Return true if this is a smallvector which has not had dynamic memory allocated for it.
const_reverse_iterator crend() const noexcept
const_iterator end() const noexcept
SmallVectorTemplateCommon(size_t Size)
const_reverse_iterator crbegin() const noexcept
pointer data() noexcept
Return a pointer to the vector's buffer, even if empty().
size_t capacity_in_bytes() const
reverse_iterator rend() noexcept
const_reverse_iterator rbegin() const noexcept
const_reference front() const
R__RVEC_NODISCARD bool empty() const
size_type size_in_bytes() const
std::reverse_iterator< const_iterator > const_reverse_iterator
size_t capacity() const noexcept
const_iterator begin() const noexcept
const_pointer data() const noexcept
Return a pointer to the vector's buffer, even if empty().
void * getFirstEl() const
Find the address of the first element.
const_reverse_iterator rend() const noexcept
RVecN(Detail::VecOps::RVecImpl< T > &&RHS)
reference operator[](size_type idx)
typename Internal::VecOps::SmallVectorTemplateCommon< T >::const_reference const_reference
RVecN operator[](const RVecN< V, M > &conds) const
RVecN(std::initializer_list< T > IL)
const_reference at(size_type pos) const
RVecN & operator=(Detail::VecOps::RVecImpl< T > &&RHS)
RVecN & operator=(RVecN &&RHS)
typename Internal::VecOps::SmallVectorTemplateCommon< T >::size_type size_type
value_type at(size_type pos, value_type fallback) const
No exception thrown. The user specifies the desired value in case the RVecN is shorter than pos.
RVecN & operator=(std::initializer_list< T > IL)
RVecN & operator=(const RVecN &RHS)
RVecN(const std::vector< T > &RHS)
RVecN(size_t Size, const T &Value)
reference at(size_type pos)
value_type at(size_type pos, value_type fallback)
No exception thrown. The user specifies the desired value in case the RVecN is shorter than pos.
typename Internal::VecOps::SmallVectorTemplateCommon< T >::reference reference
typename Internal::VecOps::SmallVectorTemplateCommon< T >::value_type value_type
const_reference operator[](size_type idx) const
A "std::vector"-like collection of values implementing handy operation to analyse them.
RVec(RVecN< T, N > &&RHS)
typename SuperClass::reference reference
RVec(const RVecN< T, N > &RHS)
RVec(size_t Size, const T &Value)
RVec & operator=(RVec &&RHS)
RVec operator[](const RVec< V > &conds) const
RVec(std::initializer_list< T > IL)
typename SuperClass::const_reference const_reference
RVec(const std::vector< T > &RHS)
typename SuperClass::size_type size_type
RVec(Detail::VecOps::RVecImpl< T > &&RHS)
typename SuperClass::value_type value_type
RVec & operator=(const RVec &RHS)
Type
enumeration specifying the integration types.
RVec< T > Reverse(const RVec< T > &v)
Return copy of reversed vector.
RVec< T > Intersect(const RVec< T > &v1, const RVec< T > &v2, bool v2_is_sorted=false)
Return the intersection of elements of two RVecs.
auto All(const RVec< T > &v) -> decltype(v[0]==false)
Return true if all of the elements equate to true, return false otherwise.
RVec< typename RVec< T >::size_type > Nonzero(const RVec< T > &v)
Return the indices of the elements which are not zero.
#define RVEC_UNARY_OPERATOR(OP)
#define RVEC_ASSIGNMENT_OPERATOR(OP)
RVec< typename RVec< T >::size_type > StableArgsort(const RVec< T > &v)
Return an RVec of indices that sort the input RVec while keeping the order of equal elements.
RVec< Common_t > Concatenate(const RVec< T0 > &v0, const RVec< T1 > &v1)
Return the concatenation of two RVecs.
R Sum(const RVec< T > &v, const R zero=R(0))
Sum elements of an RVec.
RVec< T > InvariantMasses(const RVec< T > &pt1, const RVec< T > &eta1, const RVec< T > &phi1, const RVec< T > &mass1, const RVec< T > &pt2, const RVec< T > &eta2, const RVec< T > &phi2, const RVec< T > &mass2)
Return the invariant mass of two particles given the collections of the quantities transverse momentu...
RVec< T > Take(const RVec< T > &v, const RVec< typename RVec< T >::size_type > &i)
Return elements of a vector at given indices.
RVec< T > Construct(const RVec< Args_t > &... args)
Build an RVec of objects starting from RVecs of input to their constructors.
#define RVEC_STD_BINARY_FUNCTION(F)
#define RVEC_BINARY_OPERATOR(OP)
RVec< T > Drop(const RVec< T > &v, RVec< typename RVec< T >::size_type > idxs)
Return a copy of the container without the elements at the specified indices.
size_t CapacityInBytes(const RVecN< T, N > &X)
#define RVEC_LOGICAL_OPERATOR(OP)
RVec< RVec< std::size_t > > Combinations(const std::size_t size1, const std::size_t size2)
Return the indices that represent all combinations of the elements of two RVecs.
#define RVEC_STD_UNARY_FUNCTION(F)
auto Map(Args &&... args)
Create new collection applying a callable to the elements of the input collection.
RVec< T > Where(const RVec< int > &c, const RVec< T > &v1, const RVec< T > &v2)
Return the elements of v1 if the condition c is true and v2 if the condition c is false.
auto Any(const RVec< T > &v) -> decltype(v[0]==true)
Return true if any of the elements equates to true, return false otherwise.
RVec< typename RVec< T >::size_type > Argsort(const RVec< T > &v)
Return an RVec of indices that sort the input RVec.
std::size_t ArgMin(const RVec< T > &v)
Get the index of the smallest element of an RVec In case of multiple occurrences of the minimum value...
RVec< T > StableSort(const RVec< T > &v)
Return copy of RVec with elements sorted in ascending order while keeping the order of equal elements...
double Var(const RVec< T > &v)
Get the variance of the elements of an RVec.
RVec< T > Filter(const RVec< T > &v, F &&f)
Create a new collection with the elements passing the filter expressed by the predicate.
std::size_t ArgMax(const RVec< T > &v)
Get the index of the greatest element of an RVec In case of multiple occurrences of the maximum value...
bool IsSmall(const ROOT::VecOps::RVec< T > &v)
bool IsAdopting(const ROOT::VecOps::RVec< T > &v)
auto MapImpl(F &&f, const RVec< T > &... vs) -> RVec< decltype(f(vs[0]...))>
uint64_t NextPowerOf2(uint64_t A)
Return the next power of two (in 64-bits) that is strictly greater than A.
std::size_t GetVectorsSize(const std::string &id, const RVec< T > &... vs)
auto MapFromTuple(Tuple_t &&t, std::index_sequence< Is... >) -> decltype(MapImpl(std::get< std::tuple_size< Tuple_t >::value - 1 >(t), std::get< Is >(t)...))
tbb::task_arena is an alias of tbb::interface7::task_arena, which doesn't allow to forward declare tb...
The size of the inline storage of an RVec.
Used to figure out the offset of the first element of an RVec.
Storage for the SmallVector elements.