2012-02-19 15 views
0

初期サイズを持たない構造体の配列を使用しようとすると問題が発生します。 どうすればよいですか?これは私の構造体である:C++でグローバルに動的に割り当てられた構造体

struct carbon { 
    double temp; 
    double mass; 
    rowvec::fixed<3> position;  
    rowvec::fixed<3> velocity; 
    rowvec::fixed<3> force; 
} *atom; 

私のプログラムの間、私はこのような構造体配列のサイズを割り当てています:

atom = new carbon[PARTICLE_NUM]; 

問題は、私はその後、他のファイルで、この構造体を使用する方法です。私は、ヘッダファイルを作成し、それ

extern struct carbon *atom; 

でこれを置くしかし、それは、このエラーを思い付くしました:

setup_pos.cpp:19: error: invalid use of incomplete type ‘struct carbon’ 
system_setup_distances.h:18: error: forward declaration of ‘struct carbon’ 

私はグローバル変数を使用すべきではないけど、私はちょうどしたいですまずこれをテストします。 ご協力いただきありがとうございます。

+1

なぜ動的な「配列」を使用していますか?なぜ「ベクトル」ではないのですか?それとも、普通の配列ですか? –

+0

コンパイル時にサイズを知らなくても、グローバルベクトル構造体を作成するにはどうすればよいですか? – Eddy

+0

'vector'の全体点は、そのサイズが動的であることです。私はあなたが "ベクトル構造体"の意味を理解していませんが、 –

答えて

1

​​を使用するソースファイルには、carbon構造の完全な定義が必要です。

このように、同じヘッダファイルにまとめて外部との構造を置く:あなたのソースファイルの一つで変数を定義​​

struct carbon { 
    double temp; 
    double mass; 
    rowvec::fixed<3> position;  
    rowvec::fixed<3> velocity; 
    rowvec::fixed<3> force; 
}; 

extern struct carbon *atom; 

:今

struct carbon *atom = 0; 

、いつでもあなた​​にアクセスする必要があり、構造体とextern宣言があるヘッダファイルをインクルードする必要があります。

PS。代わりに、グローバル名前空間で​​変数を持つのは、独自の名前空間にそれを置くことができます:

namespace some_clever_name 
{ 
    struct carbon { ... }; 
    extern carbon *atom; 
} 

そして、ソースファイルでこれを置く:他の回答は、あなたが必要と言うように

some_clever_name::carbon *some_clever_name::atom = 0; 
1

構造体の定義は、ヘッダファイル内にある必要があります。

1

carbonの構造体の定義をヘッダーファイルに含め、そのヘッダーファイルを不完全な型エラーが発生するファイル(.hまたは.cpp)に含める必要があります。

なぜエラーですか?
フォワード宣言を使用すると、その型はコンパイラのIncomplete型になります。これは、前方宣言されたエンティティがデータ型であることをコンパイラが知っているためですが、レイアウトや内部構造については何も知らないためですコンパイルが必要な操作を実行すると、エラーが発生した型のレイアウトが必要になります。

あなたのケースでは、コンパイラは構造体のサイズを知る必要があります。carbonは十分なメモリを割り当てることができます。これは前方宣言型であるためエラーになるためです。

+0

ええ、しかし、私は複数のファイルでその構造を使用したい場合、問題が発生します。たとえば、setup_pos.cppとsystem_setup_distances.cppでそのヘッダを使用すると、これはエラーになります。 'setup_pos.oとsystem_setup_distances.oのduplicate symbol _atom ' – Eddy

+0

@Eddy:構造体定義をヘッダとexternを使用して、グローバル・インスタンスをcppファイルに1回だけ作成します。 –

+0

@Eddy:これは、型を定義し、その型のインスタンスのポインタを1つのステートメントに作成することで、混乱してしまったからです。 –

0

ヘッダーファイルに構造体の定義をインクルードします。しかし、自分自身にが必要な理由をに聞かせてください。

C++は最初からCに基づいており、Cから継承した簡単なコンパイル戦略です。コンパイラは1回のパスを行い、コンパイラやリンカは提示されたファイル以外のものにアクセスする必要はありません。 CとUNIXが最初に開発されたとき、アドレススペースは限られていて、プロセッサはほとんどの人が想像するよりも低速でした。私のKindle Fireは、90年代まで私が使ったものよりもむしろ大きなコンピュータでした。

コンパイラをシンプルにしていたため、PL/I(Cの先祖の1人)のようなより複雑なスキームを使用するのではなく、プリプロセッサを構築してインクルードファイルを使用しました。コンパイラは構造体の "形状"を知ってコードを生成できるようにする必要があります。たとえば、massにアクセスする場合は、構造体の先頭からのオフセットを知る必要があります。だから、CとC++では、その "シェイプ"の説明をテキストで含める必要があります。

+1

'プロセッサーはほとんどの人が想像することができるよりも遅いです。いいえ、彼らはほとんどの人が想像することができないばかげた速さではありませんでした。 –

+0

さて、私はそれを認めます、私は台無しです。 –

関連する問題