14#ifndef DUMUX_PROPERTY_SYSTEM_HH 
   15#define DUMUX_PROPERTY_SYSTEM_HH 
   19#include <dune/common/std/type_traits.hh> 
   42namespace Dumux::Properties::Detail {
 
   46constexpr auto isDefinedProperty(
int)
 
   47-> 
decltype(std::integral_constant<bool, !std::is_same_v<typename P::type, UndefinedProperty>>{})
 
   52constexpr std::true_type isDefinedProperty(...) { 
return {}; }
 
   56constexpr auto hasParentTypeTag(
int)
 
   57-> 
decltype(std::declval<typename T::InheritsFrom>(), std::true_type{})
 
   62constexpr std::false_type hasParentTypeTag(...)
 
   67template<
class P, 
class T>
 
   68using TypeAliasPropertyDetector = 
typename PropertyAlias<P>::template Alias<T>;
 
   72template<
class P, 
class T>
 
   73struct TypeAliasProperty
 
   74{ 
using type = Dune::Std::detected_or_t<UndefinedProperty, TypeAliasPropertyDetector, P, T>; };
 
   77template<
class P, 
class T, 
class TypeTag>
 
   78using TemplateAliasPropertyDetector = 
typename PropertyAlias<P>::template TemplateAlias<T, TypeTag>;
 
   82template<
class P, 
class T, 
class TypeTag>
 
   83struct TemplateAliasProperty
 
   84{ 
using type = Dune::Std::detected_or_t<UndefinedProperty, TemplateAliasPropertyDetector, P, T, TypeTag>; };
 
   89using ValueMemberDetector = 
decltype(T::value);
 
   92template<
class T, 
bool hasValueMember = Dune::Std::is_detected_v<ValueMemberDetector, T>>
 
   93struct ValueMember { 
static constexpr bool value = 
false; };
 
   97struct ValueMember<T, true> { 
static constexpr auto value = T::value; };
 
  100template<
class PropertySpecialization>
 
  101struct GetPropValue { 
static constexpr auto value = ValueMember<PropertySpecialization>::value; };
 
  104template<
class P, 
class T>
 
  105struct GetPropValue<TypeAliasProperty<P, T>>
 
  106{ 
static constexpr auto value = ValueMember<typename TypeAliasProperty<P, T>::type>::value; };
 
  109template<
class P, 
class T, 
class TypeTag>
 
  110struct GetPropValue<TemplateAliasProperty<P, T, TypeTag>>
 
  111{ 
static constexpr auto value = ValueMember<typename TemplateAliasProperty<P, T, TypeTag>::type>::value; };
 
  115template<
class ...Tuples>
 
  116using ConCatTuples = 
decltype(std::tuple_cat(std::declval<Tuples>()...));
 
  119template<
class TypeTag, 
template<
class,
class> 
class Property, 
class TTagList>
 
  123template<
class TypeTag, 
template<
class,
class> 
class Property, 
class TTagList, 
class Enable>
 
  124struct GetNextTypeTag;
 
  126template<
class TypeTag, 
template<
class,
class> 
class Property, 
class LastTypeTag>
 
  127struct GetNextTypeTag<TypeTag, Property, std::tuple<LastTypeTag>, std::enable_if_t<hasParentTypeTag<LastTypeTag>(int{}), void>>
 
  128{ 
using type = 
typename GetDefined<TypeTag, Property, typename LastTypeTag::InheritsFrom>::type; };
 
  130template<
class TypeTag, 
template<
class,
class> 
class Property, 
class LastTypeTag>
 
  131struct GetNextTypeTag<TypeTag, Property, std::tuple<LastTypeTag>, std::enable_if_t<!hasParentTypeTag<LastTypeTag>(int{}), void>>
 
  132{ 
using type = UndefinedProperty; };
 
  134template<
class TypeTag, 
template<
class,
class> 
class Property, 
class FirstTypeTag, 
class ...Args>
 
  135struct GetNextTypeTag<TypeTag, Property, std::tuple<FirstTypeTag, Args...>, std::enable_if_t<hasParentTypeTag<FirstTypeTag>(int{}), void>>
 
  136{ 
using type = 
typename GetDefined<TypeTag, Property, ConCatTuples<
typename FirstTypeTag::InheritsFrom, std::tuple<Args...>>>::type; };
 
  138template<
class TypeTag, 
template<
class,
class> 
class Property, 
class FirstTypeTag, 
class ...Args>
 
  139struct GetNextTypeTag<TypeTag, Property, std::tuple<FirstTypeTag, Args...>, std::enable_if_t<!hasParentTypeTag<FirstTypeTag>(int{}), void>>
 
  140{ 
using type = 
typename GetDefined<TypeTag, Property, std::tuple<Args...>>::type; };
 
  142template<
class TypeTag, 
template<
class,
class> 
class Property, 
class LastTypeTag>
 
  143struct GetDefined<TypeTag, Property, std::tuple<LastTypeTag>>
 
  151#pragma clang diagnostic push 
  152#pragma clang diagnostic ignored "-Wdeprecated-declarations" 
  154    using LastType = Property<TypeTag, LastTypeTag>;
 
  156#pragma clang diagnostic pop 
  158    using DirectType = TypeAliasProperty<LastType, LastTypeTag>;
 
  159    using DirectTemplateType = TemplateAliasProperty<LastType, LastTypeTag, TypeTag>;
 
  161    using type = std::conditional_t<
 
  162        isDefinedProperty<LastType>(
int{}), LastType,
 
  164            isDefinedProperty<DirectTemplateType>(
int{}), DirectTemplateType,
 
  166                isDefinedProperty<DirectType>(
int{}), DirectType,
 
  167                typename GetNextTypeTag<TypeTag, Property, std::tuple<LastTypeTag>, 
void>::type
 
  173template<
class TypeTag, 
template<
class,
class> 
class Property, 
class FirstTypeTag, 
class ...Args>
 
  174struct GetDefined<TypeTag, Property, std::tuple<FirstTypeTag, Args...>>
 
  178#pragma clang diagnostic push 
  179#pragma clang diagnostic ignored "-Wdeprecated-declarations" 
  181    using FirstType = Property<TypeTag, FirstTypeTag>;
 
  183#pragma clang diagnostic pop 
  185    using DirectType = TypeAliasProperty<FirstType, FirstTypeTag>;
 
  186    using DirectTemplateType = TemplateAliasProperty<FirstType, FirstTypeTag, TypeTag>;
 
  193    using type = std::conditional_t<
 
  194        isDefinedProperty<FirstType>(
int{}), FirstType,
 
  196            isDefinedProperty<DirectTemplateType>(
int{}), DirectTemplateType,
 
  198                isDefinedProperty<DirectType>(
int{}), DirectType,
 
  199                typename GetNextTypeTag<TypeTag, Property, std::tuple<FirstTypeTag, Args...>, 
void>::type
 
  206template<
class TypeTag, 
template<
class,
class> 
class Property>
 
  209    using type = 
typename Detail::GetDefined<TypeTag, Property, std::tuple<TypeTag>>::type;
 
  210    static_assert(!std::is_same_v<type, UndefinedProperty>, 
"Property is undefined!");
 
  213template<
class TypeTag, 
template<
class,
class> 
class Property, 
class T>
 
  216    using PT = 
typename Detail::GetDefined<TypeTag, Property, std::tuple<TypeTag>>::type;
 
  217    struct WrapperT { 
using type = T; }; 
 
  218    using type = std::conditional_t<std::is_same_v<PT, UndefinedProperty>, WrapperT, PT>;
 
  221template<class ParentTag, class TypeTag, bool hasParents = hasParentTypeTag<TypeTag>(
int{})>
 
  224template<
class ParentTag, 
class TypeTag>
 
  225struct InheritsFrom<ParentTag, TypeTag, false> {
 
  226    static constexpr bool value = std::is_same_v<ParentTag, TypeTag>;
 
  229template<
class ParentTag, 
class TypeTag>
 
  230struct InheritsFrom<ParentTag, TypeTag, true> {
 
  231    static constexpr bool value = std::is_same_v<ParentTag, TypeTag>
 
  232        || InheritsFrom<ParentTag, typename TypeTag::InheritsFrom, false>::value;
 
  235template<
class ParentTag, 
class... TypeTags>
 
  236struct InheritsFrom<ParentTag, std::tuple<TypeTags...>, false> {
 
  237    static constexpr bool value = (InheritsFrom<ParentTag, TypeTags>::value || ...);
 
  250template<
class TypeTag, 
template<
class,
class> 
class Property>
 
  253    using type = 
typename Detail::GetDefined<TypeTag, Property, std::tuple<TypeTag>>::type;
 
  254    return !std::is_same_v<type, UndefinedProperty>;
 
 
  261template<
class ParentTypeTag, 
class TypeTag>
 
  264    return Detail::InheritsFrom<ParentTypeTag, TypeTag>::value;
 
 
  275template<
class TypeTag, 
template<
class,
class> 
class Property>
 
  276using GetProp = 
typename Properties::Detail::GetPropImpl<TypeTag, Property>::type;
 
  282template<
class TypeTag, 
template<
class,
class> 
class Property, 
class T>
 
  283using GetPropOr = 
typename Properties::Detail::GetPropOrImpl<TypeTag, Property, T>::type;
 
  287#pragma clang diagnostic push 
  288#pragma clang diagnostic ignored "-Wdeprecated-declarations" 
  295template<
class TypeTag, 
template<
class,
class> 
class Property>
 
  302template<
class TypeTag, 
template<
class,
class> 
class Property, 
class T>
 
  309template<
class TypeTag, 
template<
class,
class> 
class Property>
 
  310inline constexpr auto getPropValue() { 
return Properties::Detail::GetPropValue<GetProp<TypeTag, Property>>::value; }
 
  312#pragma clang diagnostic pop 
  349#define DUMUX_DEFINE_PROPERTY(Prop) \ 
  350    template<class TypeTag, class MyTypeTag> \ 
  352        using type = UndefinedProperty; \ 
  354    template<class ...Args> \ 
  355    struct PropertyAlias<Prop<Args...>> { \ 
  356        template <class MyTypeTag> using Alias = typename MyTypeTag::Prop; \ 
  357        template <class MyTypeTag, class TypeTag> using TemplateAlias = typename MyTypeTag::template Prop<TypeTag>; \ 
 
constexpr auto getPropValue()
get the value data member of a property
Definition propertysystem.hh:310
typename GetProp< TypeTag, Property >::type GetPropType
get the type alias defined in the property
Definition propertysystem.hh:296
constexpr bool hasDefinedType()
whether the property is defined/specialized for TypeTag
Definition propertysystem.hh:251
typename GetPropOr< TypeTag, Property, T >::type GetPropTypeOr
get the type alias defined in the property or the type T if the property is undefined
Definition propertysystem.hh:303
typename Properties::Detail::GetPropOrImpl< TypeTag, Property, T >::type GetPropOr
get the type of a property or the type T if the property is undefined
Definition propertysystem.hh:283
typename Properties::Detail::GetPropImpl< TypeTag, Property >::type GetProp
get the type of a property
Definition propertysystem.hh:276
constexpr bool inheritsFrom()
Return true if the given type tag inherits from the given parent type tag.
Definition propertysystem.hh:262
The energy balance equation for a porous solid.
Definition common/properties.hh:26
a tag to specify a direct alias for property extraction
Definition propertysystem.hh:33
a tag to mark properties as undefined
Definition propertysystem.hh:27