私は同じ問題に遭遇しました。私が知る限り、これは事実のようです:
クラス型のすべての静的およびグローバル変数は、初期化中の任意の時点で単一のクラスが動的割り当てを試みた場合でも、暗黙のうちに初期化に失敗します。 おそらくこれは、動的メモリに使用されている ByteBuffer がまだ利用できないためです。現時点では、1 つの電球が切れるとストランド全体がオフになる昔ながらのクリスマス ライトのストランドのようなものなので、Alchemy のエラー メッセージがより明確になることを願っています。
回避策として、問題のあるオブジェクトを発見したら、何らかの方法でその初期化を実行時まで遅らせる必要があります。頭に浮かぶ 3 つの手法は、ポインター、遅延評価関数、または配置 new で初期化されたバッファーへの参照です。
ポインター
// `global` is now a pointer
TestClass *global;
// all global variable initialization is found here now
void init_globals() {
global = new TestClass("global");
}
int main(int argc, char **argv) {
// this needs to be explicitly called at the start Alchemy
init_globals();
global
次に、コードをリファクタリングして、すべての出現箇所をtoに変更する必要があります(*global)
。
関数
// `global` is now a function
TestClass& global() {
// static locals are initialized when their functions are first called
static TestClass global_("global");
return global_;
}
global
ここで、出現するすべてを に置き換える必要がありますglobal()
。init_globals
特に、これら 3 つの手法の中で明示的な呼び出しを必要としないのはこれだけです。global()
なんらかの理由で名前を変更するのが面倒でない限り、この方法をお勧めします...その場合:
新しいプレースメント
// a memory buffer is created large enough to hold a TestClass object
unsigned char global_mem[sizeof(TestClass)];
// `global` is now a reference.
TestClass& global = *(TestClass*)(void*)global_mem;
void init_globals() {
// this initializes a new TestClass object inside our memory buffer
new (global_mem) TestClass("global");
}
int main(int argc, char **argv) {
init_globals();
このアプローチの利点は、global
と呼ばれるだけなので、他のコードを変更する必要がないことですglobal
。残念ながら、init_globals
機能を維持するのは面倒です。
編集:
後の質問で発見されたように、動的割り当てに加えて、静的ローカルを含む関数も Alchemy の初期化中に呼び出すことはできません。