6

次のクラス階層があります。

template <typename T>
class base
{
public:
   void f() {}
};

class class_a : public base<class_a> {};

class class_b : public base<class_b>, 
                public class_a 
{ 
   using base<class_b>::f; 
};

int main()
{
   class_b b;
   b.f();
   return 0;
}

Comeu と Intel C++ v11 はすべて問題ないと主張していますが、GCC (4.4.1) と VC++ 2008 は不平を言っているようです ( http://codepad.org/KQPDsqSp )。

g++ -pedantic -Wall -o test test.cpp 
test.cpp: In function ‘int main()’:
test.cpp:5: error: ‘void base<T>::f() [with T = class_b]’ is inaccessible
test.cpp:14: error: within this context 

コードはそのままで適切に形成されていると思いますが、間違っている可能性があります。SO C++ コミュニティの誰かがこの問題について何らかの洞察を提供してくれることを願っています。

注: class_b の using ディレクティブの前に「public」を追加すると、gcc と VS の両方の問題が解決されます。using ディレクティブが適用されるクラスのアクセサー セクションは、基本クラスの派生モード (パブリック、プライベート) をオーバーライドする必要がありますか?

要するにこれ

  • コンパイラ エラー - その場合、コンパイラは GCC、VS、Comeu、Intel のいずれか
  • 上記のコードは整形式ですか?
  • using ディレクティブが呼び出されるアクセサ セクションは、ベースの派生モードをオーバーライドしますか?
4

1 に答える 1

3

ここで行っているのは、シンボルをクラスのプライベート名前空間にインポートすることであいまいさを解決することです。したがって、それはメソッドのシャドウイングであり、その可視性をプライベートに変更します。プライベートとパブリックの両方でまったく同じプロトタイプを持つ 2 つの関数を持つことはできないため、f はプライベートになります。

少なくとも GCC は、を使用すると関数の可視性を変更できるはずだと考えています。

ただし、 GCCバグデータベースで見つかった漠然とした参照は、実際の使用はスコープの影響を受けないことを示しています。

最も重要なのは、直接的な回答です (C++ 標準 '03 -- 7.3.3/15)

using 宣言によって作成されたエイリアスには、メンバー宣言に対する通常のアクセシビリティがあります。

したがって、答えは次のようになります。

  • それはComeauのバグです
  • いいえ、少なくとも C++03 に関しては、コードは整形式ではありません (C++0x N3000 に関連するものは見つかりません)。
  • はい、アクセス範囲を変更できます
于 2010-02-02T01:41:34.983 に答える