3.0から放置していましたが、3.1をすっとばして、Cocos2d-x 3.2 の開発環境手順をまとめました。
3.0 で作成しているローカルのプロジェクトを3.2にアップデートする作業をしないとだめなんですが、それはまた後日・・・。
3.0から放置していましたが、3.1をすっとばして、Cocos2d-x 3.2 の開発環境手順をまとめました。
3.0 で作成しているローカルのプロジェクトを3.2にアップデートする作業をしないとだめなんですが、それはまた後日・・・。
C++11のテンプレートメソッド内で別のテンプレートを呼び出している箇所で、特定のコンパイラでコンパイル時、
error: expected primary-expression before ‘>’ token
なエラーに悩んでしまったので解決方法をメモします。
今まで見たことないので多分C++11からの仕様だと思います。
コードは以下のような感じになります。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | // テンプレートなクラス template < typename T1> class TemplateClass { public : template < typename T2> T2 func() { return T2(); } }; // テンプレートな関数 template < typename T1, typename T2> void templateFunction() { TemplateClass<T1> t; t.func<T2>(); // < ここでエラーがでます } // templateFunctionをコール void main() { templateFunction< int , float >(); } |
上記のコードをビルドするとこんなエラーが出ます。
1 2 3 4 5 6 7 | hoge.cpp: In function 'void templateFunction()': hoge.cpp:xxx:xxx: error: expected primary-expression before '>' token t.func<T2>(); ^ hoge.cpp:xxx:xxx: error: expected primary-expression before ')' token t.func<T2>(); ^ |
VisualStudioでは出ずに、gccで出ます。
templateFunction()内の
1 | t.func<T2>(); |
を以下のように書き換えるとビルドエラーが解消されます。
1 | t. template func<T2>(); |
クラスの静的コンストラクタを実現する方法を紹介します。
起動時に一度だけ行いたい処理を書く時などに便利です。
ただし、他のstaticなオブジェクトと同じく、初期化順番は保証されない点は注意してください。
ヘッダはこんな感じ。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | class Hoge { private : //! 静的コンストラクタ用のprivateな構造体 struct Construct { Construct() { // ここに初期化処理を書きます sm_hoge = 0; } }; private : static Construct sm_construct; //!< 静的コンストラクタ static int sm_hoge; }; |
cpp側はこんな感じになります。
1 2 | Hoge::Construct Hoge::sm_construct; int Hoge::sm_hoge = 0; |
ご覧のとおり、今回のパターンだとsm_hogeはもともと0で初期化しているので静的コンストラクタで処理している内容に意味はなかったりします。
Hoge.h
1 2 3 4 5 6 7 8 | class Hoge { public : static func(); private : static std::vector< int > m_vector; static std::bitset<16> m_bitset; static int m_array[16]; }; |
Hoge.cpp
1 2 3 4 5 6 | Hoge::func() { m_vector.clear(); m_bitset.reset(); m_array[0] = 0; } |
という風にしてしまうと、LNK2001の外部参照が未解決リンクエラーが出てしまいます。
staticなメンバ変数は、ヘッダ上では宣言しているだけなので、実体の確保はソース(cpp)側で行う必要があります。
Hoge.cppのfunc()の前に
1 2 3 | std::vector< int > Hoge::m_vector; std::bitset<16> Hoge::m_bitset; int Hoge::m_array[16]; |
を追記して、暗黙の初期化を行うようにすればリンクエラーは解消されます。