多态性:访问继承的类变量

时间:2010-06-23 22:33:33

标签: c++

我有一个继承自抽象基类的类。

class CStateBase
{
  friend class CApplication;
  friend class CGraphics;
  virtual int Update() =0;
};

class CStateTitle: private CStateBase
{
  friend class CApplication;
  friend class CGraphics;
  CApplication *f_App;

  int m_iR;

  int Update();

  CStateTitle(CApplication *App);
  ~CStateTitle();
};

在另一个类的方法中,CStateTitle被动态分配到CStateBase指针中。但是,如果我使用该指针尝试访问变量int m_iR,编译器会在CStateBase中查找变量,从而产生错误。如果我可以在基类中声明virtual int m_iR,我认为它可以正常工作,但由于某种原因,它不会让我声明虚拟数据成员。推荐解决此问题的方法是什么?谢谢你的帮助。

5 个答案:

答案 0 :(得分:5)

您应该从基类公开继承:

class CStateTitle: public CStateBase

否则CStateTitle 从编译器的角度来看不是 CStateBase,因此您无法通过{{1}多态访问CStateTitle个对象}指针。

您不能拥有虚拟数据成员,只能使用C ++中的虚拟方法。因此,解决方法可能是为您的数据成员声明虚拟访问器方法。

答案 1 :(得分:3)

最好的方法是将m_iR的访问抽象为某个虚函数。

另一种选择是将m_iRCStateTitle移至CStateBase。只有每个班级都需要m_iR时才有意义。

最后的选择是做一个动态演员:

CStateBase *csb = ...;

CStateTitle *cst = dynamic_cast<CStateTitle *>(csb);
if (cst)
{
    // have a valid CStateTitle
}
else
{
    // csb is not pointing at a CStateTitle, do whatever is appropriate
}

答案 2 :(得分:1)

由于您尝试直接从基类指针访问派生类的成员,因此您显然不会调用多态。因此,您可以使用dynamic_cast来访问该成员。

未经请求的建议:不要直接访问成员变量。考虑一下您的层次结构,以及如何使用虚拟方法使用某种一致的界面访问您尝试完成的操作。

答案 3 :(得分:1)

您不能拥有虚拟成员变量。

你可以在演员时改变:

CStateTitle *a = new CStateTitle();
a->m_iR = 1;
CStateBase *b = a;

或稍后使用RTTI重播

CStateBase *a = new CStateTitle();
CStateTitle *b = dynamic_cast<CStateTitle*>(a);
if( NULL != b )
  b->m_iR = 1;

或者在基类上添加一个虚拟setter方法,如果所有CStateBase都需要设置一些int。

答案 4 :(得分:0)

您可以在基类中定义虚函数以执行所需的访问(getter和/或setter),或者,您必须将基指针强制转换为派生*并从那里继续。