2016-06-18 4 views
1

何らかの方法で親が子の保護されたメンバーにアクセスできるようにすることはできますか?親アクセスの子サブプライベート/プロテクト

template <class T> 
class B { 
public : 
    void print() 
    { 
     cout << T::a << T::b << endl; 
    } 
}; 

class C : public B<C> 
{ 
protected : 
    static int a; 
    static int b; 
public : 
    C() { 
     print(); 
    } 
}; 

これは多相(仮想)のない複数のオブジェクトを継承するのに便利です。どんな提案?

編集:

の下に提案されているよう私は2つの解決策を見つける::

  • フレンドクラスとしてBを作り、
  • CRTP
  • さらにいくつかの点が考慮すべき

CRTPを使用している間は、インラインで他のコードを使用することをお勧めします。 Bコンストラクタを保護する(静的派生データアクセスの場合)ことを忘れないでください。 CRTPは、派生

最近のコンパイラに、基本クラスから静的定数データ(仮想静的定数)を転送しないように使用することができます

は、私はそれが今ではほとんどのコンパイラであると思いdevirtualizationと呼ばれる概念を使用します。

+2

BのCフレンドを作成します。 – Zereges

+0

[CRTP](https://en.wikipedia.org/wiki/Curiously_recurring_template_pattern)は逆になります! –

+0

私はこれが言われることを知っていましたが、ポイントはなぜ保護されたデータだけを述べたのかです。これは、すべての派生クラスを基本クラスのフレンドとして追加することができないため、設計ごとに有効なソリューションではありません。 –

答えて

4

これは多相(仮想)のない複数のオブジェクトを継承するのに便利です。

これはよく知られているパターンと別名静的ポリモーフィズムという名前です。

CRTPは通常、派生クラスの関数を参照するstatic_cast<T*>(this)を使用しています。

template <class T> 
class B { 
public : 
    void print() 
    { 
     cout << static_cast<T*>(this)->a << static_cast<T*>(this)->b << endl; 
      // ^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^ 
    } 
}; 

私は何とか親が子供保護されたデータへのアクセスを許可する必要があり、それは可能ですか?

もちろん可能です。これらはTpublicメンバーである必要があり、またはあなたがTB<T>friendクラスにする必要がありますへのアクセスを開くとき

class C : public B<C> 
{ 
    friend class B<C>; 
    // ^^^^^^^^^^^^^^^^^^ 
protected : 
    static int a; 
    static int b; 
public : 
    C() { 
     print(); 
    } 
}; 

Live Demo


friend宣言はまだ、class Cのカプセル化を維持します具体的なインタフェースはclass B<T>で宣言されています。

+0

私は答えが私たちはできないと思います、パブリックデータは、直接静的ではなく、このポインタによって静的にアクセスすることができます。 –

+0

@KartikV 'static'かどうかは関係ありません。それは実際に重要な範囲です。 –

+0

こんにちは、それは重要です、これは静的メンバーのためにそこにはありません。公然、残念ながらそれはすべきです。 –

関連する問題