C++ 构造函数成员初始化列表,对象切片

标签 c++ inheritance initialization polymorphism object-slicing

我有两个类(class)

class A {

public:
    virtual void doStuff() = 0;
};

class B : public A {
    int x;

public:
    virtual void doStuff() override { x = x*2;} //just example function
};

还有另一个修改和使用前一个数据的类

class Foo {
    A a;

public:
    Foo::Foo(A &a_) : a(a_) {}

};

现在我创建对象,并传递给 Foo 类

B b;
// edit b attributes, 

Foo foo(b);

所以在类构造函数的参数列表中我知道不存在对象切片的问题,因为它是一个引用,但是在分配变量 a(a_)?

因为我不知道对象 b 将存活多久,所以我需要制作一个安全拷贝。我有很多来自A的不同派生类,甚至派生自派生类。

会不会有对象切片?,

是否有解决方案,或者我需要传递指针(不想要这种方法)?

最佳答案

这会导致切片。内置多态性的 C++ 仅适用于指针/引用语义。

事实上:

class Foo {
  A a;

那甚至无法编译,因为 A不是一个具体的类。

要解决这个问题,首先制作 virtual ~A(){};然后将智能指针传递给 A大约。独特或共享。


如果失败,您可以使用自己定制的多态性。更简单的方法是填充 pImpl智能指针作为类的私有(private)成员,并在持有类中实现复制/移动语义。 pImpl可以有一个虚拟接口(interface),包装类只是将行为的不可覆盖部分转发给它。

此技术可以通过小缓冲区优化或什至有界大小的实例进行扩展,以避免堆分配。

所有这些都比直接使用内置的 C++ 对象模型更难,但它可以带来返回。

要查看这方面的著名示例,请查看 std::function<Sig>这是一种具有多态行为的值类型。

关于C++ 构造函数成员初始化列表,对象切片,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49395830/

相关文章:

c++ - VC++ 可再发行版 2012 或 2013 或 2015?

c++ - C++ 中局部变量和时间变量的区别

具有可选属性的 Java 持久性映射父类(super class)

javascript - 有没有办法将 JS 属性的 setter/getter 抽象为对象的原型(prototype)?

python类初始化

java - 基数排序最重要的优先或最不重要的,哪个更快?

c++ - new with inheritance 的不当使用?

c++ - 是否可以在 C++ 中声明具有不同类型的变量?

java - java中,为什么未初始化的char可以,但String不行

c++ - 更准确的 houghline OpenCV