2012-02-10 4 views
13

フォローアップの質問this oneコンパイラは、テンプレート引数リスト内で基本クラスのコンストラクタを選択するのはなぜですか?

基本的には、次のコードでは、なぜコンパイラはCのコンストラクタでA<B>内部BB基底クラスの(アクセス不可)コンストラクタを参照していることを考えるのですか?

struct B{}; 

template <typename T> 
struct A : private T{}; 

struct C : public A<B>{                    
    C(A<B>); // ERROR HERE 
}; 

Live example on Ideone.出力:あなたはA<B*>A<B&>あるいはA<const B>に、コンストラクタ引数を変更した場合、同じエラーがポップアップすること

prog.cpp:1:9: error: 'struct B B::B' is inaccessible
prog.cpp:7:7: error: within this context

注意。また、MSVC10、GCC 4.7、およびClang 3.1 ToTのうちの3つがエラーになるので、C++仕様の何かでなければならないことにも注意してください。 なんですか?

+0

全く同じトピックを作成した理由はわかりません。あなたはそれをより良いものにするためにそのトピックを編集できました。 – Nawaz

+3

@Nawaz:基本的には別の質問です。私は「なぜ」と尋ねる。他方の質問は「何をするか」と尋ねる。 – Xeo

+0

男、私はこれを 'class A:private NotCopyable {class B:private NotCopyable {}} 'で2回以上噛まれました。グローバルスコープを見る前に、クラススコープでシンボルを検索すると思います。 –

答えて

15

標準では、注入されたクラス名が元の名前よりアクセスしにくいことが認められています。これは、でも一緒に例を挙げて、§11.1/ 5にノートに記載されている:

[ Note: In a derived class, the lookup of a base class name will find the injected-class-name instead of the name of the base class in the scope in which it was declared. The injected-class-name might be less accessible than the name of the base class in the scope in which it was declared. —end note ]

[ Example:

class A { }; 
class B : private A { }; 
class C : public B { 
    A *p; // error: injected-class-name A is inaccessible 
    ::A *q; // OK 
}; 

end example ]

は、修飾されていないAにアクセスすることがprivate継承から来ているためアクセスできません注入された名前を、使用しています。 Aにアクセスすると、グローバルスコープでアクセス可能な宣言された名前が使用されます。

関連する問題