Home > Enterprise >  Using SFINAE to check if member exists in class based on a template
Using SFINAE to check if member exists in class based on a template

Time:06-27

The example here shows how we can use TMP to have the compiler elide functions based on whether a member exists for a given type. I want to write a metafunction that works for classes based on templates. Compilation should succeed if a class based on a template is provided in the function call that has the desired member.

The class:

template <typename KeyType>
struct RawBytesEntry
{
    bool used = false;
    size_t psl = 0;
    KeyType key;
    ...
}

I tried a whole slew of different suggestions and syntax permutations but I couldn't get it to work. Does anyone have any suggestions? Here is what I think is the "closest" I got:

template <template <typename> typename EntryType, typename = void>
struct has_psl : std::false_type
{
};

template <template <typename KeyType> typename EntryType>
struct has_psl<EntryType<KeyType>, std::void_t<decltype(EntryType<KeyType>::psl)>> : std::true_type
{
};

template <template <typename KeyType> typename EntryType, std::enable_if<has_psl<EntryType>::value>>
bool f(EntryType<KeyType> *buffer, size_t offset, EntryType<KeyType> *new_entry)

CodePudding user response:

The template parameters of the template template parameter can not be used in the body.

template <typename T, typename = void>
struct has_psl : std::false_type
{};

template <template <typename> typename EntryType, typename KeyType>
struct has_psl<EntryType<KeyType>, std::void_t<decltype(EntryType<KeyType>::psl)>> : std::true_type
{};

template <template <typename> typename EntryType, typename KeyType, std::enable_if<has_psl<EntryType<KeyType>>::value>>
bool f(EntryType<KeyType> *buffer, size_t offset, EntryType<KeyType> *new_entry) {
    return true;
}

And then,

static_assert(has_psl<int>::value == false);
static_assert(has_psl<RawBytesEntry<int>>::value == true);

Online Demo

  • Related