Commit c947cebb authored by Carsten Gräser's avatar Carsten Gräser

[!601] Add UniqueTypes_t helper template alias

Merge branch 'feature/add-uniquetypes-helper' into 'master'

ref:core/dune-common For a given `template<class...> Target` and list of types
T... the alias `UniqueTypes_t<Target, T...>` refers the instatiated template
Target<S...>, where S... is generated from T... by removing duplicate types.

This is useful for std::variant, because duplicate types are not fully
supported by some implementations. If your type list is generated by whatever
mechanism where you don't have control over uniqueness, then
`UniqueTypes_t<std::variant, T...>` is what std::variant<T...> should have
been.

See merge request [!601]

  [!601]: gitlab.dune-project.org/core/dune-common/merge_requests/601
parents a0912abe 1763ef97
Pipeline #15746 passed with stage
in 7 minutes and 35 seconds
......@@ -5,7 +5,9 @@
#include <type_traits>
#include <tuple>
#include <utility>
#include <dune/common/std/type_traits.hh>
namespace Dune {
......@@ -168,6 +170,38 @@ namespace Dune {
template<std::size_t i, class T>
using TypeListEntry_t = typename TypeListElement<i, T>::type;
namespace Impl {
template<template<class...> class Target, class ToDoList, class... Processed>
struct UniqueTypesHelper;
template<template<class...> class Target, class... Processed>
struct UniqueTypesHelper<Target, TypeList<>, Processed...>
{
using type = Target<Processed...>;
};
template<template<class...> class Target, class T0, class... T, class... Processed>
struct UniqueTypesHelper<Target, TypeList<T0, T...>, Processed...>
{
using type = std::conditional_t<
Dune::Std::disjunction<std::is_same<T0, Processed>...>::value,
typename UniqueTypesHelper<Target, TypeList<T...>, Processed...>::type,
typename UniqueTypesHelper<Target, TypeList<T...>, T0, Processed...>::type>;
};
} // namespace Impl
/** \brief Remove duplicates from a list of types
*
* For a given list of types T... instantiate Target<S...>, where
* S... is generated by removing duplicate types from T... . This
* is useful for std::variant which does not like to be instantiated
* with duplicate types.
*/
template<template<class...> class Target, class... T>
using UniqueTypes_t = typename Impl::UniqueTypesHelper<Target, TypeList<T...>>::type;
} // namespace Dune
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment