7

静的変数を事前に宣言してから使用する必要がある場合があります。しかし、この宣言の変数名が間違っている可能性があり、コンパイラーはそれを検出できません、おっと!

例:

/* lots of codes */
static some_type some_name; /* pre-declaration */
                            /* but it may define "some_name" */
/* use some_name */

/* lots of codes */

static some_type someName = initialization; /* definition */
/* use someName */

/* lots of codes */

「some_name」と「someName」は異なります。最初に間違った変数を使用しています。事前宣言ステートメントで何も定義されていない場合、コンパイラーは誤りを検出します。

では、静的変数を宣言するが、それを定義しない方法は?コンパイラが間違った名前を検出できるようにする新しい宣言に事前宣言を変更するにはどうすればよいですか?

4

6 に答える 6

9

gccあなたが説明した場合に警告を出します:

./x.c:3010: warning: 'someName' defined but not used

解決策:現在行っていることを実行しますが、コンパイラの警告を無視しないでください;)

編集:

更新された質問で:いいえ、静的変数を(定義せずに)単純に宣言する方法はないと思います。

一般的な解決策は、すべてのグローバルスコープ変数が1回だけ宣言され、必要に応じてイニシャライザーが宣言されるようにすることです。

于 2009-12-08T04:41:53.437 に答える
8
static some_type some_name; /*definition */

静的変数some_nameは0で初期化されています。それは単なる宣言ではなく、定義です。

IMO、静的変数は、そのリンケージが常に内部であるため、extern指定子を使用してCで宣言することはできません。

于 2009-12-08T04:41:46.107 に答える
4

C言語の内部リンケージを持つオブジェクトの非定義宣言(つまり、用語では「事前宣言」)を作成することはできません。

あなたがそれに近づくことができる限り、あなたがあなたの例で持っているものである暫定的な定義があります。ただし、タイプミスの場合、暫定的な定義は、リンカーエラーではなく、暗黙的に独立した定義を生成します。

于 2009-12-08T05:26:06.393 に答える
2

少し背景:

他の人が指摘しているように、静的変数には内部リンケージがあります。つまり、静的変数は同じ「コンパイル単位」またはソースファイルでのみ使用できます。つまり、ヘッダーファイルで宣言したり、あるコンパイルユニットで値を割り当てたり、その値が別のコンパイルユニットに表示されることを期待したりすることはできません。

グローバル変数(静的または非静的)を初期化すると、コンパイラーは、変数に割り当てられたメモリー位置にある実行可能ファイルに初期値を入れるだけです。つまり、常に初期値があります。もちろん、割り当てステートメントを使用して、後でいつでも値をオーバーライドできます。

提案:

コンパイル時に変数の値が本当にわからない場合は、初期化関数で動的に割り当てる必要があります。

static some_type some_variable; /* = 0 by default */

/* some code */

void MyInitializations()
{
    some_variable = some_value;
}

変数を1つの場所、たとえばヘッダーファイルで宣言し、それをソースファイルで定義する場合は、「extern」宣言を使用して、変数がどこにあるかを気にしないようにコンパイラーに指示する必要があります。リンカは、別のファイルで関数を見つけてアドレスを入力するのと同じように、変数の場所を見つけます。

ヘッダ:

extern some_type some_variable;

ソースファイル1:

void UseSomeVariable()
{
    x = some_variable;
}

ソースファイル2:

some_type some_variable = some_value;

/* possible also uses some_variable */

ある場所で変数を宣言し、別の場所で定義したいだけの場合は、「static」キーワードを使用しないでください。これの欠点は、異なるコンパイル単位(.cファイル)で同じグローバル変数を使用できず、ヘッダーファイルで使用できないことです。

于 2009-12-08T04:59:39.330 に答える
0

変数を事前に宣言する必要がありますか?そうでない場合は、初期化子を唯一の宣言に配置します。初期化子が定数でない場合(C、IIRCではなくC ++が必要)、それを使用する一部の関数の前に事前宣言する必要がある理由を理解できます。ただし、初期化子に必要なものはすべて、その前に事前に宣言することができます。

したがって、定数defと静的変数を各ファイルの先頭に配置して、静的変数の初期化子が定数の直後に来るようにします。その場合、個別の初期化行は必要ありません。

それ以外の場合、cafの権利:警告を利用するためだけに、コードをgccでコンパイルする価値がある場合があります。私はC++のMFCGUIのg++に対してそれを行いました。(コンパイル、実行ではありません!)

AFAIK Cには、後で初期化子を使用した定義がない場合にエラーを生成する弱い定義を記述する方法がありません。変数はBSSセクションに入るので、常に暗黙の0があります。

于 2009-12-08T04:49:47.963 に答える
-1

私があなたの問題を理解しているなら、たぶんあなたはそれを正しい方向に向けていないのかもしれません。

あなたのプログラムにどちらがいいかわかりませんか?extern SomeType someVar_;私はこの変数が知られていることを知っていますが、それが今何であるかをあなたに伝えたくありません。

したがって、別のファイルで変数を宣言することができます

static SomeType SomeVar_;

あなたのファイルに、

extern SomeType SomeVar_

そして、あなたが望むところに初期化を置くより。

于 2009-12-08T04:57:00.303 に答える