我在一些 C++ 代码中遇到了一些棘手的问题,这最容易使用代码来描述。我有类似的课程:
class MyVarBase
{
}
class MyVar : public MyVarBase
{
int Foo();
}
class MyBase
{
public:
MyBase(MyVarBase* v) : m_var(v) {}
virtual MyVarBase* GetVar() { return m_var; }
private:
MyVarBase* m_var;
}
我还有一个 MyBase 的子类,它需要有一个 MyVar 类型的成员,因为它需要调用 Foo。将 Foo 函数移至 MyVarBase 不是一个选择。这样做有意义吗:
class MyClass : public MyBase
{
public:
MyClass(MyVar* v) : MyBase(v), m_var(v) {}
MyVar* GetVar() { return m_var; }
private:
MyVar* m_var;
}
这似乎有效,但看起来非常糟糕,我不确定它是否会导致内存泄漏或破坏复制构造函数。我的其他选择可能是将 MyClass 中的 MyVar 变量命名为其他名称,但使其等于基类中的 m_var 指针,或者在 MyVar 类型上模板化 MyBase。
所有这些选项似乎都不理想,所以我想知道是否有其他人遇到过这样的情况,以及是否有好的方法可以使其发挥作用。
正确的方法是仅在基类中使用该变量。正如派生类所知,它必须是动态类型MyVar
,这是完全合理的:
class MyClass : public MyBase
{
public:
MyClass(MyVar* v) : MyBase(v) {}
MyVar* GetVar() { return static_cast<MyVar*>(MyBase::GetVar()); }
}
由于 MyVar 派生自 MyVarBase,因此不同的返回类型GetVar
如果 GetVar 是虚拟的,仍然可以工作(就像这里的情况一样)。请注意,使用该方法时,不能有任何函数MyBase
显然,这可以将指针重置为不同的东西。
注意static_cast
在这种情况下是正确的演员阵容。使用dynamic_cast
正如一位评论者所提议的那样,它将告诉 GetVar 的读者和用户:MyBase::GetVar()
可以返回一个指向非 MyVar 类型的对象的指针。但这并不反映我们的意图,因为您只会传递 MyVar。在软件开发中,结果是最重要的。你什么could要做的就是断言它是非空的。它将在运行时中止,并在项目的调试版本中显示错误消息:
MyVar* GetVar() {
assert(dynamic_cast<MyVar*>(MyBase::GetVar()) != 0);
return static_cast<MyVar*>(MyBase::GetVar());
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)