29 sort(r.begin(), r.end());
44auto appendUnique(std::ranges::random_access_range
auto& r, T&& v) {
45 static_assert(std::is_same_v<
typename decltype(begin(r))::value_type, std::remove_reference_t<
decltype(v)>>);
46 const auto it = find(begin(r), end(r), v);
47 size_t index = std::distance(begin(r), it);
49 r.push_back(std::forward<T>(v));
65 std::ranges::for_each(c, [&os](
auto&& var) { os << var <<
'\n'; });
78 auto transformValueToPointer = [](
auto&& obj) {
return &obj; };
79 return (std::ranges::subrange(cont.begin(), cont.end()) | std::views::transform(transformValueToPointer));
93 auto transformValueToPointer = [](
auto&& obj) ->
auto& {
return *obj; };
94 return (std::ranges::subrange(cont.begin(), cont.end()) | std::views::transform(transformValueToPointer));
99template <
typename... Types>
104 template <
class Tuple, std::size_t... I>
105 constexpr auto makeTupleSubsetImpl(Tuple&& t, std::index_sequence<I...>) {
106 return std::make_tuple(std::get<I>(std::forward<Tuple>(t))...);
109 template <
class Tuple, std::size_t... I>
110 constexpr auto makeTupleFromTupleIndicesImpl(Tuple&& t, std::index_sequence<I...>) {
111 return std::make_tuple(std::get<I>(std::forward<Tuple>(t))...);
114 template <
typename T,
typename... Ts>
115 struct uniqueImpl : std::type_identity<T>
119 template <
typename... Ts,
typename U,
typename... Us>
120 struct uniqueImpl<
std::tuple<Ts...>, U, Us...>
121 : std::conditional_t<(std::is_same_v<U, Ts> || ...), uniqueImpl<std::tuple<Ts...>, Us...>,
122 uniqueImpl<std::tuple<Ts..., U>, Us...>>
126 template <
typename... Ts>
127 using unique_tupleImpl =
typename uniqueImpl<std::tuple<>, Ts...>::type;
129 template <
typename T,
typename... Types>
130 auto makeNestedTupleFlatImpl() {
131 constexpr bool isTuple = traits::isSpecialization<std::tuple, T>::value;
132 if constexpr (
sizeof...(Types) > 0) {
133 if constexpr (isTuple)
136 return std::tuple_cat(std::make_tuple(T()), makeNestedTupleFlatImpl<Types...>());
138 if constexpr (isTuple)
141 return std::make_tuple(T());
145 template <
typename T,
typename... Types>
146 auto makeNestedTupleFlatAndStoreReferencesImpl(
const std::tuple<T, Types...>& tup) {
147 constexpr bool isTuple = traits::isSpecialization<std::tuple, std::remove_cvref_t<T>>::value;
148 if constexpr (
sizeof...(Types) > 0) {
149 if constexpr (isTuple)
150 return std::tuple_cat(
151 makeNestedTupleFlatAndStoreReferencesImpl(std::get<0>(tup)),
153 [](
const T&,
const Types&... args) {
154 return makeNestedTupleFlatAndStoreReferencesImpl(std::make_tuple(std::cref(args)...));
158 return std::tuple_cat(
159 std::make_tuple(std::cref(std::get<0>(tup))),
161 [](
const T&,
const Types&... args) {
162 return makeNestedTupleFlatAndStoreReferencesImpl(std::make_tuple(std::cref(args)...));
166 if constexpr (isTuple)
167 return makeNestedTupleFlatAndStoreReferencesImpl(std::get<0>(tup));
169 return std::make_tuple(std::cref(std::get<0>(tup)));
173 template <
typename T,
typename... Types>
174 auto makeNestedTupleFlatAndStoreReferencesNonConstImpl(
const std::tuple<T, Types...>& tupconst) {
175 auto& tup =
const_cast<std::tuple<T, Types...
>&>(tupconst);
176 constexpr bool isTuple = traits::isSpecialization<std::tuple, std::remove_cvref_t<T>>::value;
177 if constexpr (
sizeof...(Types) > 0) {
178 if constexpr (isTuple)
179 return std::tuple_cat(
180 makeNestedTupleFlatAndStoreReferencesNonConstImpl(std::get<0>(tup)),
182 [](T&, Types&... args) {
183 return makeNestedTupleFlatAndStoreReferencesNonConstImpl(std::make_tuple(std::ref(args)...));
187 return std::tuple_cat(
188 std::make_tuple(std::ref(std::get<0>(tup))),
190 [](T&, Types&... args) {
191 return makeNestedTupleFlatAndStoreReferencesNonConstImpl(std::make_tuple(std::ref(args)...));
195 if constexpr (isTuple)
196 return makeNestedTupleFlatAndStoreReferencesNonConstImpl(std::get<0>(tup));
198 return std::make_tuple(std::ref(std::get<0>(tup)));
219template <
typename Tuple,
typename Predicate>
220constexpr size_t find_if(Tuple&& tuple, Predicate pred) {
221 size_t index = std::tuple_size<std::remove_reference_t<Tuple>>::value;
222 size_t currentIndex = 0;
225 Dune::Hybrid::forEach(tuple, [&](
auto&& value) {
226 if (!found && pred(value)) {
227 index = currentIndex;
247template <
typename Tuple,
typename Predicate>
249 return find_if(tuple, pred) == std::tuple_size<std::decay_t<Tuple>>::value;
264template <
typename Tuple,
typename Predicate>
265bool any_of(Tuple&& tuple, Predicate pred) {
283template <
typename Tuple,
typename Predicate>
284auto filter(Tuple&& tuple, Predicate pred) {
286 [&pred](
auto... ts) {
287 return std::tuple_cat(std::conditional_t<pred(ts), std::tuple<
decltype(ts)>, std::tuple<>>{}...);
303template <
typename... Types>
304constexpr auto unique([[maybe_unused]] std::tuple<Types...>&& tuple) {
305 return Impl::unique_tupleImpl<Types...>();
321template <
typename Tuple,
typename Predicate>
322constexpr size_t count_if(Tuple&& tuple, Predicate pred) {
324 Dune::Hybrid::forEach(tuple, [&](
auto&& value) {
343template <
template <
auto...>
class Type,
typename Tuple>
345 return find_if(std::remove_cvref_t<Tuple>(),
346 []<
typename T>(T&&) {
return traits::isSpecializationNonTypes<Type, std::remove_cvref_t<T>>::value; });
361template <
template <
auto...>
class Type,
typename Tuple>
363 constexpr int index = findTypeSpecialization<Type, Tuple>();
364 static_assert(index < std::tuple_size_v<std::remove_cvref_t<Tuple>>,
365 "The found index has to be smaller than the tuple size");
366 return std::get<index>(tuple);
382template <
template <
auto...>
class Type,
typename Tuple>
384 return (
find_if(std::remove_cvref_t<Tuple>(), []<
typename T>(T&&) {
385 return traits::isSpecializationNonTypes<Type, std::remove_cvref_t<T>>::value;
386 }) < std::tuple_size_v<std::remove_cvref_t<Tuple>>);
400template <
template <
auto...>
class Type,
typename Tuple>
403 Tuple(), []<
typename T>(T&&) {
return traits::isSpecializationNonTypes<Type, std::remove_cvref_t<T>>::value; });
417template <
template <
auto...>
class Type,
typename Tuple>
432template <
int N,
class Tuple>
434 static_assert(N < std::tuple_size_v<std::remove_reference_t<Tuple>>,
435 "The requested size needs to be smaller than the size of the tuple.");
437 return Impl::makeTupleSubsetImpl(std::forward<Tuple>(t), std::make_index_sequence<N>{});
453template <
class Tuple, std::size_t... I>
455 return Impl::makeTupleFromTupleIndicesImpl(std::forward<Tuple>(t), std::index_sequence<I...>{});
465template <
typename... Types>
467 return decltype(Impl::makeNestedTupleFlatImpl<Types...>())();
479template <
typename Tuple>
481 if constexpr (std::tuple_size_v<std::remove_cvref_t<Tuple>> == 0)
483 else if constexpr (!std::is_const_v<std::remove_reference_t<Tuple>>)
484 return Impl::makeNestedTupleFlatAndStoreReferencesNonConstImpl(std::forward<Tuple>(tup));
486 return Impl::makeNestedTupleFlatAndStoreReferencesImpl(std::forward<Tuple>(tup));
499 if constexpr (!std::is_same_v<T, std::nullptr_t>)
Contains stl-like type traits.
auto getSpecialization(Tuple &&tuple)
Gets the specialization of the given template type from the tuple.
Definition: algorithms.hh:362
auto appendUnique(std::ranges::random_access_range auto &r, T &&v)
Appends a value to the range if it is not already present.
Definition: algorithms.hh:44
constexpr auto unique(std::tuple< Types... > &&tuple)
Creates a tuple with unique types from the given tuple.
Definition: algorithms.hh:304
void printContent(C &&c, std::ostream &os=std::cout)
Prints the contents of a container to the specified output stream.
Definition: algorithms.hh:64
constexpr auto makeTupleSubset(Tuple &&t)
Creates a subset tuple with the first N elements from the given tuple.
Definition: algorithms.hh:433
bool none_of(Tuple &&tuple, Predicate pred)
Checks if none of the elements in the tuple satisfy a given predicate.
Definition: algorithms.hh:248
constexpr int findTypeSpecialization()
Finds the index of the first element in the tuple that is a specialization of the given template type...
Definition: algorithms.hh:344
static constexpr bool countTypeSpecialization_v
Variable template for counting the occurrences of a specialization of a template type in a tuple.
Definition: algorithms.hh:418
void makeUniqueAndSort(std::ranges::random_access_range auto &r)
Sorts and removes duplicate elements from a random access range.*.
Definition: algorithms.hh:28
auto transformValueRangeToPointerRange(C &cont)
Transforms a value range to a pointer range.
Definition: algorithms.hh:77
auto transformPointerRangeToReferenceRange(C &cont)
Transforms a pointer range to a reference range.
Definition: algorithms.hh:92
bool any_of(Tuple &&tuple, Predicate pred)
Checks if any of the elements in the tuple satisfy a given predicate.
Definition: algorithms.hh:265
auto filter(Tuple &&tuple, Predicate pred)
Filters the elements of a tuple based on a given predicate.
Definition: algorithms.hh:284
constexpr bool countTypeSpecialization()
Counts the occurrences of a specialization of a template type in a tuple.
Definition: algorithms.hh:401
constexpr size_t count_if(Tuple &&tuple, Predicate pred)
Counts the number of elements in the tuple satisfying the given predicate.
Definition: algorithms.hh:322
constexpr bool hasTypeSpecialization()
Checks if a tuple has a specialization of a template type.
Definition: algorithms.hh:383
constexpr auto makeTupleFromTupleIndices(Tuple &&t)
Creates a new tuple using indices from the original tuple.
Definition: algorithms.hh:454
constexpr size_t find_if(Tuple &&tuple, Predicate pred)
Finds the index of the first element in the tuple satisfying a predicate.
Definition: algorithms.hh:220
Definition: algorithms.hh:17
auto makeNestedTupleFlatAndStoreReferences(Tuple &&tup)
Creates a flattened nested tuple and stores references.
Definition: algorithms.hh:480
auto makeNestedTupleFlat(std::tuple< Types... >)
Creates a flattened nested tuple.
Definition: algorithms.hh:466
auto & returnReferenceOrNulloptIfObjectIsNullPtr(T v)
Returns a reference or std::nullopt if the object is a nullptr.
Definition: algorithms.hh:498
Concept to check if a type is a pointer or nullptr_t.
Definition: traits.hh:28