gpt4 book ai didi

c++ - 扩展现有的 C++ 类

转载 作者:太空狗 更新时间:2023-10-29 21:16:03 25 4
gpt4 key购买 nike

我想在不更改现有类的情况下添加额外的功能。

说,

class base{
public:
int i;
base(){i = 1;}
virtual void do_work(){ /*Do some work*/ }
};

如果我想给它添加序列化成员函数,我会简单地创建一个派生类

class derived : public base{
public:
void serialize();
};

void derived::serialize(){
cout << "derived class" << endl;
}

我确实需要处理现有的 base 对象,例如

int main(){
base a;
derived & b = static_cast<derived &>(a);

b.serialize();
}

这个例子运行没有问题。但我知道通过 static_cast 进行的 downcast 通常是要避免的。

但是我想知道这个特定用例的downcast 是否可以被认为是安全的,因为derived 类只有一个额外的成员函数。访问 vtable 是否会有一些潜在的未定义行为?

最佳答案

您扩展 Base 的方式并没有使用 vtable,因为您没有 virtual 方法。将其视为 Derived has A Base 可能更容易;您创建了一个包含 Base 成员变量的新类。

我的建议。

模板函数

我个人会选择模板函数。您可以保留原始问题中的所有工作,并避免需要向您的类添加 virtual 调用。

template<typename T>
void serialize_object(T& t)
{
t.serialize()
}

然后根据你的例子。

Derivied d;
serialize_object(d);

最大的好处是您无需在此处添加运行时转换。如果您传递的对象没有 serialize 方法,编译器会通知您。

虚拟化

如果你真的想通过虚拟接口(interface)来处理这个问题,那就去做吧。

struct Serializable{
virtual void serialize()=0;
virtual ~Serializable(){}
}

class Derived : public Serializable {
public:
void serialize() override;
}

void Derivied::serialize()
{
std::cout << "Yah\n";
}

然后在你的代码中。

Derivied d;
Serializable& s = dynamic_cast<Serializable&>(d);

然而,这里最大的问题是谁是您的基类的所有者?他们提供了虚拟dtor吗?如果不是,那么使用 std::unique_ptrstd::shared_ptr 可能会导致您无法直接处理接口(interface)。

关于c++ - 扩展现有的 C++ 类,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36227712/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com