我可以在派生类中将私有成员子类化吗?

时间:2013-01-01 11:20:13

标签: c++ inheritance

我有一个基础数据成员类:

class DataClass {
}

和一个子类:

class DerivedDataClass : public DataClass {
}

我使用DataClass作为类的私有成员DataClassList

class DataClassList {
  public:
    // some useful functions here
  private:
    DataClass private_data;
}

我想继承DataClassList来创建一个可以在DerivedDataClass上运行的类

class DerivedDataClassList : public DataClassList {
  // how do i get this class to use DerivedDataClass as the private member?
}

这可以用C ++中的某种形式完成吗?

编辑: 在我正在尝试做的事情上添加一些注释:

DataClass有一些有用的功能,我不想在DerivedDataClass中重新定义,DerivedDataClass具有自己的功能。所以,继承是有道理的。到目前为止一切都很好。

下一个层面是问题。 DataClassList具有依赖于DataClass函数的有用函数。 DerivedDataClassList除了基类提供的有用功能外,还需要从DerivedDataClass 访问数据/运行函数。

无法将DataClass中的私人DataClassList成员更改为DerivedDataClass,我无法在DerivedDataClass中调用DerivedDataClassList中的内容。

3 个答案:

答案 0 :(得分:3)

基本上,你没有。私人意味着私人 - 它只属于那个阶级。正确的方法是拥有一个访问器功能。

如果这个类有特殊要求访问该成员,那么它应该受到保护[然而,这是一个相当愚蠢的概念,因为它根本不提供任何保护 - 任何想要到达该领域的人都需要从班级派生,瞧,他们可以自由访问]。

感谢jogojapan指出我错过了一点。使用模板的答案是一个解决方案。另一种是在基类中使用指针,然后使用访问器函数将private_data设置为提供的类成员。哪个“正确”取决于你想做什么。例如,如果它是某种元素的列表(例如图形对象(窗口,菜单等)或游戏对象),并且您实际上希望它们是一个列表[或几个类似的列表],那么使用指针是正确的解。如果你有几种从不以常见方式使用的不同类型的对象,那么模板类可能是正确的方法。

答案 1 :(得分:2)

只要你为此使用继承,你就会从基类中获得private_data成员作为派生类的成员,尽管是一个不可访问的成员。您无法更改派生类中基类成员的数据类型。

我相信在你的情况下使用类模板更好:

template <typename Data>
class DataClassList
{
public:
  /*...*/
private:
  Data private_data;
};

您只需要在上面编写一次定义,但您可以按如下方式创建实例:

DataClassList<DataClass>         standard_list;
DataClassList<DerivedDataClass>  derived_list;

前者是一个包含DataClass成员的对象,后者是一个包含DerivedDataClass成员的对象(没有其他成员)。

答案 2 :(得分:1)

我假设您要在DataClass中使用private_data对象DerivedDataClassList。 如果您想使用DerivedDataClass,那么您需要在某处声明DerivedDataClass的对象(我在任何地方都看不到DerivedDataClass的对象)。或者您需要继承DerivedDataClass - 我再次在代码中看不到。

class DataClassList 
{
    protected:
        DataClass private_data;
};

class DerivedDataClassList : private DataClassList 
{
    // DataClass object private_data is like a private member here
};

如果您将private_data作为protected DataClassList成员而不是privateDataClassList成为private base class DerivedDataClassList private_data然后private就像DerivedDataClassList的{​​{1}}成员一样。

如果您的原始问题没有输错,并且您确实希望DerivedDataClass对象成为私有成员,那么您可以使用指针。

class DataClassList 
{
    public:
        DataClassList(DataClass * p) : private_data(p) {}
    protected:
        DataClass * private_data;
};

class DerivedDataClassList : private DataClassList 
{
    public:
    DerivedDataClassList():DataClassList(new DerivedDataClass) { }

    // private_data which a pointer to a DerivedDataClass object is like a private member here. 
};