鉴于以下情况:
template <typename T>
class Whatever
{
public:
Whatever(T &&t): _t(std::move(t)) { }
private:
T _t;
};
当T
是指针类型时,我需要检查构造函数的t
arg以查看它是-1
(不要问),并将其更改为{{1在将其分配给nullptr
之前。
换句话说,我需要为指针类型重载此构造函数。
有谁知道这是否可行?
注意:即使我在指针类型上部分地专门化类,我希望该类在可能的情况下继承上述类本身(因为除了这两个类的行为相同),但不知道是否这是可能的。任何帮助,将不胜感激。感谢。
答案 0 :(得分:5)
您可以使用标记分派和委托构造函数:
#include <type_traits>
template <typename T>
class Whatever
{
public:
Whatever(T&& t)
: Whatever(std::move(t), std::is_pointer<T>{})
{
}
private:
Whatever(T&& t, std::true_type)
: _t(/*initialize _t as a pointer*/)
{
}
Whatever(T&& t, std::false_type)
: _t(/*initialize _t as a non-pointer*/)
{
}
T _t;
};
答案 1 :(得分:3)
您可以使用std::enable_if<...>
并处理重载集。 更容易不专门化构造函数,只是以不同的方式进行适当的转换:
template <typename T>
class WhateverBase {
protected:
T _t;
WhateverBase(T&& t): _t(std::move(t)) {}
};
template <typename T>
class WhateverBase<T*> {
protected:
T* _t;
WhateverBase(T* t): _t(adjust(t)) {}
};
template <typename T>
class Whatever: WhateverBase<T>
{
public:
Whatever(T&& t): WhateverBase(std::move(t)) {}
// ...
};
上述逻辑假设Whatever
中有其他代码,这些代码在使用不同类型T
的版本之间共享,不应复制。
或者,可以创建一个move()
的自定义版本来执行逻辑:
template <typename T>
std::remove_reference_t<T>&& adjust_move(T&& ref) {
return static_cast<std::remove_reference_t<T>&&>(ref);
}
template <typename T>
T* adjust_move(T* ref) { return adjust(ref); }
Whatever<T>::Whatever(T&& t): _t(adjust_move(t)) {}
(实际上,这种方法更简单......)。
...并在构造函数中使用它来代替std::move(t)
。