如何检测例如。T::is_transparent 已定义?

dar*_*une 0 c++ sfinae template-meta-programming

是否有用于测试的通用模板/宏,例如。如果定义了名称,那么一些东西。如何is_transparent运作。

is_transparent使比较器透明std::set(即可以使用自定义类型查找/等)。它只需要定义为任何东西,例如。using is_transparent = void;

我希望为某些自定义类型做类似的事情,但理想情况下我会使用某些东西(甚至是宏),或者我可以使用有关实现的指导。

问题是,如何根据限定名称测试类型是否定义(存在?)?

Hol*_*Cat 5

使用检测习惯用法:

#include <iostream>
#include <experimental/type_traits>

struct A {};

struct B
{
    using is_transparent = void; // Any other type works too.
};

template <typename T> using detect_transparent = typename T::is_transparent;

int main()
{
    std::cout << std::experimental::is_detected_v<detect_transparent, A> << '\n'; // 0
    std::cout << std::experimental::is_detected_v<detect_transparent, B> << '\n'; // 1
}
Run Code Online (Sandbox Code Playgroud)

is_detected_v是来自所谓的库基础 TS v2的实验性功能。

如果你的编译器不支持,或者你不喜欢experimental在代码中看到这个词,你可以自己实现:

namespace impl
{
    template <typename T, typename ...P>
    struct dependent_type {using type = T;};

    // `std::void_t` used to be broken in Clang (probably it no longer is),
    // so I use a custom safe replacement instead.
    template <typename A, typename ...B>
    using void_type = typename dependent_type<void, A, B...>::type;

    template <typename DummyVoid, template <typename...> typename A, typename ...B>
    struct is_detected : std::false_type {};

    template <template <typename...> typename A, typename ...B>
    struct is_detected<void_type<A<B...>>, A, B...> : std::true_type {};
}

template <template <typename...> typename A, typename ...B>
inline constexpr bool is_detected_v = impl::is_detected<void, A, B...>::value;
Run Code Online (Sandbox Code Playgroud)