diff --git a/Redcraft.Utility/Source/Private/Testing/Templates.cpp b/Redcraft.Utility/Source/Private/Testing/Templates.cpp index f42f948..6154439 100644 --- a/Redcraft.Utility/Source/Private/Testing/Templates.cpp +++ b/Redcraft.Utility/Source/Private/Testing/Templates.cpp @@ -1001,13 +1001,13 @@ void TestTuple() { TTuple TempA = { 1, 'A' }; - TempA.Visit([](auto&& A) { A++; }); + TempA.Visit([](auto&& A) -> void { ++A; }); TempA.Visit( [] (T&& A) { - if constexpr (CSameAs) always_check(A == 2); - else if constexpr (CSameAs) always_check(A == 'B'); + if constexpr (CSameAs) always_check(A == 2 ); + else if constexpr (CSameAs) always_check(A == 'B'); else always_check_no_entry(); } ); diff --git a/Redcraft.Utility/Source/Public/Templates/Tuple.h b/Redcraft.Utility/Source/Public/Templates/Tuple.h index 5e38496..3734fd9 100644 --- a/Redcraft.Utility/Source/Public/Templates/Tuple.h +++ b/Redcraft.Utility/Source/Public/Templates/Tuple.h @@ -278,28 +278,37 @@ struct TTTupleSynthThreeWayComparable, TTypeSequence<>> : FTrue template concept CTTupleSynthThreeWayComparable = TTTupleSynthThreeWayComparable::Value; -template -struct TTupleVisitElementByIndex; - -template -struct TTupleVisitElementByIndex> +template +struct TTupleVisitElementByIndex { - template - FORCEINLINE static constexpr decltype(auto) Do(F&& Func, TTupleType&& Arg, size_t Index) + template + struct TInvokeElement { - if (Index == I) return InvokeResult(Forward(Func), Forward(Arg).template GetValue()); - return TTupleVisitElementByIndex>::Do(Forward(Func), Forward(Arg), Index); - } -}; + FORCEINLINE static constexpr Ret Do(F&& Func, TTupleType&& Arg) + { + return InvokeResult(Forward(Func), Forward(Arg).template GetValue()); + } + }; -template -struct TTupleVisitElementByIndex> -{ - template - FORCEINLINE static constexpr decltype(auto) Do(F&& Func, TTupleType&& Arg, size_t) + template + struct TInvokeTuple; + + template + struct TInvokeTuple> { - checkf(false, "Read access violation. Please check Index."); - return InvokeResult(Forward(Func), Forward(Arg).template GetValue<0>()); + FORCEINLINE static constexpr Ret Do(F&& Func, TTupleType&& Arg, size_t Index) + { + using FInvokeImplType = Ret(*)(F&&, TTupleType&&); + + constexpr FInvokeImplType InvokeImpl[] = { TInvokeElement::Do... }; + + return InvokeImpl[Index](Forward(Func), Forward(Arg)); + } + }; + + FORCEINLINE static constexpr Ret Do(F&& Func, TTupleType&& Arg, size_t Index) + { + return TInvokeTuple>::Do(Forward(Func), Forward(Arg), Index); } }; @@ -421,64 +430,64 @@ public: template NODISCARD FORCEINLINE constexpr decltype(auto) GetValue() const volatile&& { return static_cast(*this).GetValue>(); } /** Invoke the callable object 'Func' with a tuple of arguments. */ - template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) & { return FHelper::Apply(Forward(Func), static_cast< TTuple& >(*this)); } - template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) const & { return FHelper::Apply(Forward(Func), static_cast(*this)); } - template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) volatile& { return FHelper::Apply(Forward(Func), static_cast< volatile TTuple& >(*this)); } - template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) const volatile& { return FHelper::Apply(Forward(Func), static_cast(*this)); } - template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) && { return FHelper::Apply(Forward(Func), static_cast< TTuple&&>(*this)); } - template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) const && { return FHelper::Apply(Forward(Func), static_cast(*this)); } - template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) volatile&& { return FHelper::Apply(Forward(Func), static_cast< volatile TTuple&&>(*this)); } - template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) const volatile&& { return FHelper::Apply(Forward(Func), static_cast(*this)); } + template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) & { return FHelper::Apply(Forward(Func), static_cast< TTuple& >(*this)); } + template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) const & { return FHelper::Apply(Forward(Func), static_cast(*this)); } + template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) volatile& { return FHelper::Apply(Forward(Func), static_cast< volatile TTuple& >(*this)); } + template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) const volatile& { return FHelper::Apply(Forward(Func), static_cast(*this)); } + template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) && { return FHelper::Apply(Forward(Func), static_cast< TTuple&&>(*this)); } + template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) const && { return FHelper::Apply(Forward(Func), static_cast(*this)); } + template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) volatile&& { return FHelper::Apply(Forward(Func), static_cast< volatile TTuple&&>(*this)); } + template requires (CInvocable) FORCEINLINE constexpr decltype(auto) Apply(F&& Func) const volatile&& { return FHelper::Apply(Forward(Func), static_cast(*this)); } /** Visits each element in a tuple in parallel and applies it as arguments to the function. */ - template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) & { VisitTuple(Forward(Func), static_cast< TTuple& >(*this)); } - template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) const & { VisitTuple(Forward(Func), static_cast(*this)); } - template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) volatile& { VisitTuple(Forward(Func), static_cast< volatile TTuple& >(*this)); } - template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) const volatile& { VisitTuple(Forward(Func), static_cast(*this)); } - template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) && { VisitTuple(Forward(Func), static_cast< TTuple&&>(*this)); } - template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) const && { VisitTuple(Forward(Func), static_cast(*this)); } - template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) volatile&& { VisitTuple(Forward(Func), static_cast< volatile TTuple&&>(*this)); } - template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) const volatile&& { VisitTuple(Forward(Func), static_cast(*this)); } + template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) & { VisitTuple(Forward(Func), static_cast< TTuple& >(*this)); } + template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) const & { VisitTuple(Forward(Func), static_cast(*this)); } + template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) volatile& { VisitTuple(Forward(Func), static_cast< volatile TTuple& >(*this)); } + template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) const volatile& { VisitTuple(Forward(Func), static_cast(*this)); } + template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) && { VisitTuple(Forward(Func), static_cast< TTuple&&>(*this)); } + template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) const && { VisitTuple(Forward(Func), static_cast(*this)); } + template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) volatile&& { VisitTuple(Forward(Func), static_cast< volatile TTuple&&>(*this)); } + template requires (true && ... && CInvocable) FORCEINLINE constexpr void Visit(F&& Func) const volatile&& { VisitTuple(Forward(Func), static_cast(*this)); } /** Visits specified element in a tuple and applies it as arguments to the function. */ - template requires ((sizeof...(Ts) >= 1 && CCommonReference...>) && ... && (CInvocable)) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) & { return static_cast< TTuple& >(*this).Visit...>>(Forward(Func), Index); } - template requires ((sizeof...(Ts) >= 1 && CCommonReference...>) && ... && (CInvocable)) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) const & { return static_cast(*this).Visit...>>(Forward(Func), Index); } - template requires ((sizeof...(Ts) >= 1 && CCommonReference...>) && ... && (CInvocable)) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) volatile& { return static_cast< volatile TTuple& >(*this).Visit...>>(Forward(Func), Index); } - template requires ((sizeof...(Ts) >= 1 && CCommonReference...>) && ... && (CInvocable)) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) const volatile& { return static_cast(*this).Visit...>>(Forward(Func), Index); } - template requires ((sizeof...(Ts) >= 1 && CCommonReference...>) && ... && (CInvocable)) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) && { return static_cast< TTuple&&>(*this).Visit...>>(Forward(Func), Index); } - template requires ((sizeof...(Ts) >= 1 && CCommonReference...>) && ... && (CInvocable)) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) const && { return static_cast(*this).Visit...>>(Forward(Func), Index); } - template requires ((sizeof...(Ts) >= 1 && CCommonReference...>) && ... && (CInvocable)) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) volatile&& { return static_cast< volatile TTuple&&>(*this).Visit...>>(Forward(Func), Index); } - template requires ((sizeof...(Ts) >= 1 && CCommonReference...>) && ... && (CInvocable)) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) const volatile&& { return static_cast(*this).Visit...>>(Forward(Func), Index); } + template requires (((sizeof...(Ts) >= 1) && ... && CInvocable) && CCommonReference...>) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) & { checkf(Index < Num(), "Read access violation. Please check Index."); return static_cast< TTuple& >(*this).Visit...>>(Forward(Func), Index); } + template requires (((sizeof...(Ts) >= 1) && ... && CInvocable) && CCommonReference...>) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) const & { checkf(Index < Num(), "Read access violation. Please check Index."); return static_cast(*this).Visit...>>(Forward(Func), Index); } + template requires (((sizeof...(Ts) >= 1) && ... && CInvocable) && CCommonReference...>) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) volatile& { checkf(Index < Num(), "Read access violation. Please check Index."); return static_cast< volatile TTuple& >(*this).Visit...>>(Forward(Func), Index); } + template requires (((sizeof...(Ts) >= 1) && ... && CInvocable) && CCommonReference...>) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) const volatile& { checkf(Index < Num(), "Read access violation. Please check Index."); return static_cast(*this).Visit...>>(Forward(Func), Index); } + template requires (((sizeof...(Ts) >= 1) && ... && CInvocable) && CCommonReference...>) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) && { checkf(Index < Num(), "Read access violation. Please check Index."); return static_cast< TTuple&&>(*this).Visit...>>(Forward(Func), Index); } + template requires (((sizeof...(Ts) >= 1) && ... && CInvocable) && CCommonReference...>) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) const && { checkf(Index < Num(), "Read access violation. Please check Index."); return static_cast(*this).Visit...>>(Forward(Func), Index); } + template requires (((sizeof...(Ts) >= 1) && ... && CInvocable) && CCommonReference...>) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) volatile&& { checkf(Index < Num(), "Read access violation. Please check Index."); return static_cast< volatile TTuple&&>(*this).Visit...>>(Forward(Func), Index); } + template requires (((sizeof...(Ts) >= 1) && ... && CInvocable) && CCommonReference...>) FORCEINLINE constexpr decltype(auto) Visit(F&& Func, size_t Index) const volatile&& { checkf(Index < Num(), "Read access violation. Please check Index."); return static_cast(*this).Visit...>>(Forward(Func), Index); } /** Visits specified element in a tuple and applies it as arguments to the function. */ - template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) & { return NAMESPACE_PRIVATE::TTupleVisitElementByIndex>::Do(Forward(Func), static_cast< TTuple& >(*this), Index); } - template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) const & { return NAMESPACE_PRIVATE::TTupleVisitElementByIndex>::Do(Forward(Func), static_cast(*this), Index); } - template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) volatile& { return NAMESPACE_PRIVATE::TTupleVisitElementByIndex>::Do(Forward(Func), static_cast< volatile TTuple& >(*this), Index); } - template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) const volatile& { return NAMESPACE_PRIVATE::TTupleVisitElementByIndex>::Do(Forward(Func), static_cast(*this), Index); } - template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) && { return NAMESPACE_PRIVATE::TTupleVisitElementByIndex>::Do(Forward(Func), static_cast< TTuple&&>(*this), Index); } - template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) const && { return NAMESPACE_PRIVATE::TTupleVisitElementByIndex>::Do(Forward(Func), static_cast(*this), Index); } - template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) volatile&& { return NAMESPACE_PRIVATE::TTupleVisitElementByIndex>::Do(Forward(Func), static_cast< volatile TTuple&&>(*this), Index); } - template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) const volatile&& { return NAMESPACE_PRIVATE::TTupleVisitElementByIndex>::Do(Forward(Func), static_cast(*this), Index); } + template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) & { checkf(Index < Num(), "Read access violation. Please check Index."); return NAMESPACE_PRIVATE::TTupleVisitElementByIndex::Do(Forward(Func), static_cast< TTuple& >(*this), Index); } + template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) const & { checkf(Index < Num(), "Read access violation. Please check Index."); return NAMESPACE_PRIVATE::TTupleVisitElementByIndex::Do(Forward(Func), static_cast(*this), Index); } + template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) volatile& { checkf(Index < Num(), "Read access violation. Please check Index."); return NAMESPACE_PRIVATE::TTupleVisitElementByIndex::Do(Forward(Func), static_cast< volatile TTuple& >(*this), Index); } + template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) const volatile& { checkf(Index < Num(), "Read access violation. Please check Index."); return NAMESPACE_PRIVATE::TTupleVisitElementByIndex::Do(Forward(Func), static_cast(*this), Index); } + template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) && { checkf(Index < Num(), "Read access violation. Please check Index."); return NAMESPACE_PRIVATE::TTupleVisitElementByIndex::Do(Forward(Func), static_cast< TTuple&&>(*this), Index); } + template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) const && { checkf(Index < Num(), "Read access violation. Please check Index."); return NAMESPACE_PRIVATE::TTupleVisitElementByIndex::Do(Forward(Func), static_cast(*this), Index); } + template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) volatile&& { checkf(Index < Num(), "Read access violation. Please check Index."); return NAMESPACE_PRIVATE::TTupleVisitElementByIndex::Do(Forward(Func), static_cast< volatile TTuple&&>(*this), Index); } + template requires ((sizeof...(Ts) >= 1) && ... && CInvocableResult) FORCEINLINE constexpr Ret Visit(F&& Func, size_t Index) const volatile&& { checkf(Index < Num(), "Read access violation. Please check Index."); return NAMESPACE_PRIVATE::TTupleVisitElementByIndex::Do(Forward(Func), static_cast(*this), Index); } /** Transform a tuple into another tuple using the given function. */ - template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) & { return FHelper::Transform(Forward(Func), static_cast< TTuple& >(*this)); } - template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) const & { return FHelper::Transform(Forward(Func), static_cast(*this)); } - template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) volatile& { return FHelper::Transform(Forward(Func), static_cast< volatile TTuple& >(*this)); } - template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) const volatile& { return FHelper::Transform(Forward(Func), static_cast(*this)); } - template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) && { return FHelper::Transform(Forward(Func), static_cast< TTuple&&>(*this)); } - template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) const && { return FHelper::Transform(Forward(Func), static_cast(*this)); } - template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) volatile&& { return FHelper::Transform(Forward(Func), static_cast< volatile TTuple&&>(*this)); } - template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) const volatile&& { return FHelper::Transform(Forward(Func), static_cast(*this)); } + template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) & { return FHelper::Transform(Forward(Func), static_cast< TTuple& >(*this)); } + template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) const & { return FHelper::Transform(Forward(Func), static_cast(*this)); } + template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) volatile& { return FHelper::Transform(Forward(Func), static_cast< volatile TTuple& >(*this)); } + template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) const volatile& { return FHelper::Transform(Forward(Func), static_cast(*this)); } + template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) && { return FHelper::Transform(Forward(Func), static_cast< TTuple&&>(*this)); } + template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) const && { return FHelper::Transform(Forward(Func), static_cast(*this)); } + template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) volatile&& { return FHelper::Transform(Forward(Func), static_cast< volatile TTuple&&>(*this)); } + template requires (true && ... && (CInvocable && !CSameAs>)) NODISCARD FORCEINLINE constexpr decltype(auto) Transform(F&& Func) const volatile&& { return FHelper::Transform(Forward(Func), static_cast(*this)); } /** Constructs an object of type T with a tuple as an argument. */ - template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() & { return FHelper::template Construct(static_cast< TTuple& >(*this)); } - template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() const & { return FHelper::template Construct(static_cast(*this)); } - template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() volatile& { return FHelper::template Construct(static_cast< volatile TTuple& >(*this)); } - template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() const volatile& { return FHelper::template Construct(static_cast(*this)); } - template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() && { return FHelper::template Construct(static_cast< TTuple&&>(*this)); } - template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() const && { return FHelper::template Construct(static_cast(*this)); } - template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() volatile&& { return FHelper::template Construct(static_cast< volatile TTuple&&>(*this)); } - template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() const volatile&& { return FHelper::template Construct(static_cast(*this)); } + template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() & { return FHelper::template Construct(static_cast< TTuple& >(*this)); } + template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() const & { return FHelper::template Construct(static_cast(*this)); } + template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() volatile& { return FHelper::template Construct(static_cast< volatile TTuple& >(*this)); } + template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() const volatile& { return FHelper::template Construct(static_cast(*this)); } + template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() && { return FHelper::template Construct(static_cast< TTuple&&>(*this)); } + template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() const && { return FHelper::template Construct(static_cast(*this)); } + template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() volatile&& { return FHelper::template Construct(static_cast< volatile TTuple&&>(*this)); } + template requires (CConstructibleFrom) NODISCARD FORCEINLINE constexpr T Construct() const volatile&& { return FHelper::template Construct(static_cast(*this)); } /** @return The number of elements in the tuple. */ NODISCARD static FORCEINLINE constexpr size_t Num() { return sizeof...(Ts); }