Specializing C++ template based on presence/absense of a class member?

隐身守侯 提交于 2019-12-18 04:12:26

问题


Consider the following:

struct A {
  typedef int foo;
};

struct B {};

template<class T, bool has_foo = /* ??? */>
struct C {};

I want to specialize C so that C<A> gets one specialization and C<B> gets the other, based on the presence or absence of typename T::foo. Is this possible using type traits or some other template magic?

The problem is that everything I've tried produces a compile error when instantiating C<B> because B::foo doesn't exist. But that's what I want to test!


Edit: I think ildjarn's answer is better, but I finally came up with the following C++11 solution. Man is it hacky, but at least it's short. :)

template<class T>
constexpr typename T::foo* has_foo(T*) {
  return (typename T::foo*) 1;
}
constexpr bool has_foo(...) {
  return false;
}
template<class T, bool has_foo = (bool) has_foo((T*)0)>

回答1:


Another (C++03) approach:

template<typename T>
struct has_foo
{
private:
    typedef char no;
    struct yes { no m[2]; };

    static T* make();
    template<typename U>
    static yes check(U*, typename U::foo* = 0);
    static no check(...);

public:
    static bool const value = sizeof(check(make())) == sizeof(yes);
};

struct A
{
    typedef int foo;
};

struct B { };

template<typename T, bool HasFooB = has_foo<T>::value>
struct C
{
    // T has foo
};

template<typename T>
struct C<T, false>
{
    // T has no foo
};



回答2:


Something like this might help: has_member.

typedef char (&no_tag)[1]; 
typedef char (&yes_tag)[2];

template< typename T > no_tag has_member_foo_helper(...);

template< typename T > yes_tag has_member_foo_helper(int, void (T::*)() = &T::foo);

template< typename T > struct has_member_foo {
    BOOST_STATIC_CONSTANT(bool
        , value = sizeof(has_member_foo_helper<T>(0)) == sizeof(yes_tag)
        ); }; 

template<class T, bool has_foo = has_member_foo<T>::value> 
struct C {};


来源:https://stackoverflow.com/questions/10354774/specializing-c-template-based-on-presence-absense-of-a-class-member

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!