C++单一构造函数模板专业化

gex*_*ide 1 c++ templates constructor template-specialization

对不起,如果这是一个骗局.有许多类似的问题,但似乎没有人真正解决这个问题.他们都有点不同.

所以我想要实现的目标:考虑一个模板类X<T>.现在,我想要一个额外的构造函数为该模板的特定instanciattion延伸,让我们说指针X<T*>.我不想创建一个完整的模板规范X<T*>,因为它X<T*>应该与通常的模板完全一样(并且该模板是巨大的,因此复制粘贴将是一个相当重复的代码复制气味),只是它有一个额外的构造函数.我也不想X<T*>继承,X<T>因为我不想在这两者之间建立子类型关系.这可能吗?我试过这样的:

template<T> class X{};

template<T> X<T*>::X(int i){...}
Run Code Online (Sandbox Code Playgroud)

但它没有编译.这有点可能吗?

mfo*_*ini 5

你可以使用SFINAE做这样的事情:

#include <iostream>
#include <type_traits>

template<class T> class X{
public:
    X(int i) {
        init();
    }
private:
    template<class U = T>
    typename std::enable_if<std::is_pointer<U>::value>::type init() {
        std::cout << "It's a pointer!\n";
    }

    template<class U = T>
    typename std::enable_if<!std::is_pointer<U>::value>::type init() {
        std::cout << "It's not a pointer!\n";
    }
};

int main() {
    X<int> a(1);
    X<int*> b(2);
}
Run Code Online (Sandbox Code Playgroud)

哪个输出:

It's not a pointer!
It's a pointer!
Run Code Online (Sandbox Code Playgroud)

你没有重载构造函数,但你实现了你想要的.

请注意,您需要C++ 11才能使用此代码.

编辑:好的,这段代码完全符合您的要求:

#include <iostream>
#include <type_traits>

template<class T> class X{
public:
    template<class U = T, class enabler = typename std::enable_if<std::is_pointer<U>::value, T>::type>
    X(int i) {
        std::cout << "It's a pointer!\n";
    }

    template<class U = T, class enabler = typename std::enable_if<!std::is_pointer<U>::value, T*>::type>
    X() {
        std::cout << "It's not a pointer!\n";
    }
};

int main() {
    X<int> a;
    X<int*> b(2);
}
Run Code Online (Sandbox Code Playgroud)

其中仍然输出与以前相同.请注意,这不是一个很好的设计.根据模板参数设置一些构造函数是奇怪的.这段代码解决了你的问题.