有没有一种方法可以将类型封装在模板类中(类似于 std::optional
),它具有所有必要的特殊构造函数和赋值运算符(即复制构造函数/赋值,移动ctor/assignment),但只有在底层类型具有这些功能时才“启用”它们? type_traits
中的函数(如 std::is_copy_constructible
)看起来可能会有所帮助,但我不确定如何使用它们来实现此目标。作为引用,我尝试实现的类型类似于 std::optional
但替代值只是“无”,我想使用自定义错误类型。例如
template <typename T>
class ErrorOr {
public:
enum class Error {
FATAL,
WARNING,
NONE,
};
ErrorOr(T val) : val(val), error(Error::NONE) {}
ErrorOr(Error error) : error(error) {}
// TODO: Implement copy/move ctors/assignment operators that only
// exist if they do for the underlying T
T get() { val; }
private:
T val;
Error error;
};
这是一个非常简单/最小的实现,没有很多必要的功能,但希望能说明我要表达的观点。
这在 C++11 中可能吗?
最佳答案
在这种情况下,什么都不做。 ErrorOr<T>
拥有类型为 T
的成员将默认所有特殊成员函数做正确的事。如果T
不可复制,ErrorOr<T>
也不会。
但是,这也不是真正的可选类型,因为您总是有一个 T
.如果您最终转向有条件地具有 T
的实现,
一种方法是从一个空类型继承,该类型根据需要启用或禁用特殊成员。
一个简化的版本是:
template <bool allowCopies>
struct copy_enabler {
copy_enabler() = default;
copy_enabler(copy_enabler const& ) = default;
copy_enabler& operator=(copy_enabler const& ) = default;
};
template <>
struct copy_enabler<false> {
copy_enabler() = default;
copy_enabler(copy_enabler const& ) = delete;
copy_enabler& operator=(copy_enabler const& ) = delete;
};
然后你可以简单地:
template <typename T>
class ErrorOr : private copy_enabler</* is T copyable */> { ... };
在实践中,您将希望对所有特殊成员函数执行此操作,并添加一个标记类型,这样如果您对多个不同的类模板使用此技巧,它们就不会共享一个公共(public)基类。
关于c++ - 仅当底层类型具有这些构造函数时才实现模板类型构造函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48389981/