我有一个类,我想在其上使用构建器模式,但它派生 self 需要访问其属性的基类。我不能在我的实现中访问 BaseClass
的成员而不公开它们,即使我从 BaseClass
或其他同样臭的东西派生 Builder 也是如此。我的类(class):
基类.h:
class BaseClass
{
protected:
CString name;
}
派生类.h:
class DerivedClass : public BaseClass
{
public:
// builder starts here and has the same base class as the class it is nested in
// (if it doesn't, we can't get access to name)
static class Builder : public BaseClass
{
public:
Builder::Builder(CString pName)
{
this->name = pName;
}
Builder Builder::Description(CString pDescription)
{
this->description = pDescription;
return *this;
}
};
public:
CString description;
};
派生类.cpp:
DerivedClass::DerivedClass(Builder builder)
{
this->name = builder.name; // this is NOT ok
this->description = builder.description; // this is ok
}
我的问题是我无法访问 builder.name
。 Visual Studio 说“ protected 成员 BaseClass::name
不能通过 DerivedClass::Builder
指针或对象访问”。我试过让 Builder
成为 BaseClass
的 friend
,但无济于事。这post也提供了一个解决方法,但它是针对 Java 的,而且非常困惑。
在 C++ 中是否有一种使用带有继承的构建器模式的合适方法?
最佳答案
即使 Builder
是在 DerivedClass
中声明的,Builder
也不是隐含的 DerivedClass
的 friend ,就像你一样正在期待。 Builder
仍然是它自己的类,它遵循与任何其他类相同的规则,包括范围访问规则。这就是默认情况下 DerivedClass
无法访问 Builder
的 protected
成员的原因。您需要明确声明这种友元。
此外,您的 Builder::Description()
方法将无法按原样工作,因为 Builder
没有 description
成员。 Builder
方法中的 this
指针仍然指向 Builder
实例,而不是 DerivedClass
实例。如果您希望 Builder
访问 DerivedClass
的成员,则需要为其提供一个指向 DerivedClass
实例的指针。否则,为 Builder
提供它自己的 description
成员(看起来您无论如何都在尝试这样做)。
试试这个:
基类.h:
class BaseClass
{
protected:
CString name;
};
派生类.h:
class DerivedClass : public BaseClass
{
public:
class Builder : public BaseClass
{
public:
Builder(const CString &pName)
{
this->name = pName;
}
Builder& Description(const CString &pDescription)
{
this->description = pDescription;
return *this;
}
public:
CString description; // <-- add this
friend class DerivedClass; // <-- add this
};
public:
DerivedClass(const Builder &builder);
public:
CString description;
};
派生类.cpp:
DerivedClass::DerivedClass(const DerivedClass::Builder &builder)
{
this->name = builder.name; // this is ok now
this->description = builder.description; // this is ok now
}
关于具有继承性的 C++ 构建器模式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17554618/