this ポインタ以外の基底クラスオブジェクトの protected メンバについて#
C++ のクラスにおける protected メンバは派生クラスからアクセスできると思っていたが、少し追加の条件があった。
C++ リファレンスのアクセス指定子の説明 から引用すると、protected メンバへアクセスできるのは
Base のメンバおよびフレンド。
Base から派生したあらゆるクラスのメンバおよびフレンド (C++17未満)。ただし Base から派生した型のオブジェクト (this を含みます) に対する操作のときだけです。
となっている。ここで、派生クラス自身のオブジェクトの protected メンバでなければ使えないという制限があることに注意。
例えば、次のようなソースコードはコンパイルできない。
class Base {
protected:
void func();
};
class Derived : public Base {
void process(const Base& obj) {
obj.func(); // ←ココでアクセスできない。
}
};
上記のようなことがしたい場合は、次のようにする。
class Base {
protected:
void func();
static void call_func(const Base& obj) {
obj.func();
}
};
class Derived : public Base {
void process(const Base& obj) {
call_func(obj);
}
};
基底クラス自身は自分の protected メンバへアクセスできる上に、基底クラスの protected な static 関数は派生クラスからアクセスできるため、上記のソースコードはコンパイルできる。上記なら friend 指定のように private なメンバへのアクセスとかまで許可しなくて良い。