C++ Builder Pattern with Inheritance

builder, builder-pattern, c++, c++builder

Solution

Even though `Builder` is declared inside of `DerivedClass`, `Builder` is not implicitly friends with `DerivedClass`, like you are expecting. `Builder` is still its own class, and it follows the same rules as any other class, including scope access rules. That is why `DerivedClass` cannot access `protected` members of `Builder` by default. You need to explicitly declare that friendship.

Also, your `Builder::Description()` method will not work as-is because `Builder` does not have a `description` member. The `this` pointer inside of `Builder` methods still refers to the `Builder` instance, not a `DerivedClass` instance. If you want the `Builder` to access members of `DerivedClass`, it needs to be given a pointer to a `DerivedClass` instance. Otherwise, give `Builder` its own `description` member (which it looks like you were attempting to do anyway).

Try this:

BaseClass.h:

class BaseClass
{
protected:
    CString name;
};

DerivedClass.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;
};

DerivedClass.cpp:

DerivedClass::DerivedClass(const DerivedClass::Builder &builder)
{
    this->name = builder.name; // this is ok now
    this->description = builder.description; // this is ok now
}

Problem

I have a class I would like to use the builder pattern on, but it is derived from a base class whose attributes I need to access. I can't access the members of `BaseClass` in my implementation without making them public, even if I derive Builder from `BaseClass` or something equally smelly. My classes: BaseClass.h: ``` class BaseClass { protected: CString name; } ``` DerivedClass.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; }; ``` DerivedClass.cpp: ``` DerivedClass::DerivedClass(Builder builder) { this->name = builder.name; // this is NOT ok this->description = builder.description; // this is ok } ``` My problem is that I can't access `builder.name`. Visual Studio says that "protected member `BaseClass::name` is not accessible through a `DerivedClass::Builder` pointer or object". I've tried fiddling around with making `Builder` a `friend` of `BaseClass`, but to no avail. This post has also provided a workaround, but it's for Java, and very messy. Is there a decent way to use the builder pattern with inheritance in C++?

Original source