c++ - 防止切片的惯用方法?

标签 c++ inheritance object-slicing

有时,c++ 默认允许切片可能会令人烦恼。例如

struct foo { int a; };
struct bar : foo { int b; };

int main() {
    bar x{1,2};
    foo y = x; // <- I dont want this to compile!
}

这个 compiles and runs as expected !不过,如果我不想启用切片怎么办?

编写 foo 的惯用方法是什么,这样就不能对任何派生类的实例进行切片?

最佳答案

我不确定它是否有一个命名习惯用法,但您可以向重载集添加一个已删除的函数,该函数比基类切片操作更匹配。如果您将 foo 更改为

struct foo 
{ 
    int a; 
    foo() = default; // you have to add this because of the template constructor

    template<typename T>
    foo(const T&) = delete; // error trying to copy anything but a foo

    template<typename T>
    foo& operator=(const T&) = delete; // error assigning anything else but a foo
};

那么您只能复制构造或将 foo 复制分配给 foo。任何其他类型都会选择函数模板,并且您会收到有关使用已删除函数的错误。这确实意味着您的类和使用它的类不再是一个聚合。由于添加的成员是模板,因此它们不被视为复制构造函数或复制赋值运算符,因此您将获得默认的复制和移动构造函数和赋值运算符。

关于c++ - 防止切片的惯用方法?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55600025/

相关文章:

c++ - 如何将C++模板方法的返回类型声明为其他类中静态方法的返回类型?

c++ - C++ 切片的潜在解决方法?

c++ - 学习 C++ : returning references AND getting around slicing

c++ - ld64.so 存在于 ldd 中,在运行时丢失

android - 如何防止我的 android jni 调用中的代码停滞?

使用 float 时 CSS 显示不继承

c# - C# 中单个属性的多个属性的继承

c++ - 从 .dat 文件中读取数字,然后计算标准差

class - Smalltalk 中的 self 和 super