2013-06-13 27 views
9

ある名前空間のenumの別名を別の名前空間に導入しようとしています。エイリアス化された型の変数を宣言できますが、コンパイラ(gcc 4.1.2)は列挙型の値を認識しません。エラー: 'ワン' が 'B' のメンバーではありませんC++のtypedefとenums

namespace A 
{ 
    enum a { One = 1, Two = 2 }; 
} 

namespace B 
{ 
    typedef enum A::a b; 
}; 

A::a a_value = A::One; // Pretty standard 
B::b b_value = B::One; // Does not work 
B::b c_value = A::One; // Clearly B is a typedef for A 

int main (int argc, const char *argv[]) 
{ 
    return 0; 
} 

コンパイルエラーが

test.cc:12です。

+0

A :: aをbとしてみてください。名前空間Bの内側(またはそのようなもの)。 (これがコメントであり、答えではない理由です) – jmucchiello

+4

これは、 'One'が** Bのメンバーではないからです... –

+0

これは本当に古いコンパイラです。あなたは本当にこのバージョンを使用する必要がありますか? – stefan

答えて

7

列挙型がbを通じてBにアクセス可能ですが、値ではないと明示的に持ち込まれている必要があります

namespace B { 
    typedef A::a b; 
    using A::One; 
} 

私は別のusing文なしでそれらすべてを持って来るための方法はないと思いますそれぞれusing namespace A;を実行しないか、列挙型の名前空間に列挙して、そのためのusingステートメントを持っていない限り、後者は、Aのすべてを持ち込むことを心配していて、ちょうどA::valueで列挙型の値を使用したい場合は、これが望ましいかもしれません。ここに例があります:

namespace A 
{ 
    inline namespace en { 
     enum a { One = 1, Two = 2 }; 
    } 

    enum c {Three}; 
} 

namespace B 
{ 
    using namespace A::en; 
    typedef A::a b; 
} 

A::a a_value = A::One; // works; things in en are still visible in A 
B::b b_value = B::One; // works; en was brought into B 
B::b c_value = A::One; // works 
A::c meh = B::Three; //fails; only en was brought into B 

インラインネームスペースは、GCC 4.1.2でサポートされていないC++ 11で導入されたことに注意してください。可能であれば、アップグレードを強くお勧めします。最新の安定版リリースは4.8.1です。

0

C++ 11より前のC++では、その問題の(単純な)解決策は提供されていません。 C++ 11では、列挙型は、次の構文を使用して、スコープ宣言することがあります。

enum struct a { /* .... */ }; // the class keyword may also be used 

効果が列挙子(定数)を作ることですつまり、列挙型自体の中にスコープ。 aの定数にアクセスする表記は、例えばa::Oneになります。これらは現在名前空間ではなく列挙型に属しているため、列挙型とともに型定義付きの別の名前空間に簡単にインポートできます。ただし、スコープ付きenum値は通常のenumと同じようにintに簡単に昇格できないことに注意してください。

namespace A { 
    enum class a { One = 1, Two = 2 }; 
} 

namespace B { 
    typedef A::a b; 
} 

A::a a_value = A::One; 
B::b b_value = B::One; // Now this works 
B::b c_value = A::One; // Clearly B is still a typedef for A 

int main (int argc, const char *argv[]) { 
    return 0; 
}