変数が同時に定義され、割り当てられました
-
13-09-2019 - |
質問
コーディングスタイルのプレゼンテーションは、それらが定義されている場合変数は(デフォルト値に)割り当てられるべきではないことを提唱しました。代わりに、彼らはちょうど彼らの使用前にデフォルト値を割り当てる必要があります。 だから、のようなもの。
int a = 0;
ひんしゅくを買うべきです。
もちろん、「int型の例は単純化ですが、同じことがまた、ポインタなどのような他のタイプのために、以下ます。
また、それはまた、C99互換コンパイラは、現在、上述の場合に警告を投げることを述べた。
上記のアプローチは、あなただけ使用する前にそれらをmemsetの、すなわち構造のため、私には便利になります。構造のみエラー脚に用いられる(又は充填)されている場合、これは効率的であろう。
他のすべてのケースでは、私は私があるため、未初期化ポインタの両方のコードを書き、維持しながら、多くのバグに遭遇したとして、慎重な運動を定義し、デフォルト値に割り当てる見つけます。さらに、私はコンストラクタを介してC ++は、同じアプローチ、すなわち定義及び割り当てを提唱信じる。
C99標準では定義&割り当てる好きではない(場合)私はなぜ疑問に思って。コーディングスタイルのプレゼンテーションが提唱何やっでの任意のかなりのメリットですか?
解決
通常私は彼らが定義されている場合、変数を初期化をお勧めしたい、と値がない場合は初期化されていない変数を残します。どちらにしても、ルールは許可するスコープとしての使用に近い入れます。
その代わりに、彼らはちょうど彼らの使用前にデフォルト値を割り当てる必要があります。
通常、あなたは、すべてのデフォルト値を使用しないでください。 C99では、コードと宣言を混在させることができますので、あなたがそれに値を代入する前に変数を定義しない点はありません。あなたはそれを取ることになっています値を知っている場合は、デフォルト値を持つことにも意味がありません。
また、それはまた、C99互換コンパイラは、現在、上述の場合に警告を投げることを述べた。
ケースのためにあなたが表示されません - あなたはint x = 0;
を持つための警告を得ることはありません。私は強く、誰かがこれが混ざってしまったと思われます。コンパイラは、あなたがそれに値を割り当てずに変数を使用している場合に警告し、あなたが持っている場合:
... some code ...
int x;
if ( a )
x = 1;
else if ( b )
x = 2;
// oops, forgot the last case else x = 3;
return x * y;
あなたは、xは、少なくともgccで、初期化されずに使用することができることを警告が表示されます。
あなたがx
前if
に値を割り当てる場合は、警告を得ることはありませんが、割り当てがイニシャライザとして、あるいは別々のステートメントとして行われているかどうかは無関係です。
、最初のxにデフォルト値を割り当てない点は、ありません。
他のヒント
の無のようにC99での要件(あるいは私の知ることを、ガイドライン)、またコンパイラはそれについて警告を表示しないはありません。それは単にスタイルの問題です。
限りコーディングスタイルに関しては、私はあなたがあまりにも文字通りのものを取ったと思います。たとえば、あなたの文は次のような場合には権利である...
int i = 0;
for (; i < n; i++)
do_something(i);
...あるいは中...
int i = 1;
[some code follows here]
while (i < a)
do_something(i);
...しかし、私の心の中で、より良い「宣言し、割り当てる」早期に処理されるように、他の例もあります。スタックまたは様々なOOPの構造上に構築された構造、などを考えてみます:
struct foo {
int bar;
void *private;
};
int my_callback(struct foo *foo)
{
struct my_struct *my_struct = foo->private;
[do something with my_struct]
return 0;
}
または(C99構造体の初期化子)のように:
void do_something(int a, int b, int c)
{
struct foo foo = {
.a = a,
.b = b + 1,
.c = c / 2,
};
write_foo(&foo);
}
私は一種の私は標準がそれについて何も言うまったくわからないにもかかわらず、アドバイスに同意し、私は非常に多くのコンパイラの警告についてのビットが真である疑います。
事は、現代のコンパイラは初期化されていないと、変数の使用を検出することができない、です。あなたは初期化時のデフォルト値にあなたの変数を設定する場合は、その検出を失います。そして、デフォルト値があまりにもバグを引き起こす可能性があります。確かにあなたの例、int a = 0;
の場合インチ誰0
がa
のために適切な値であると言う?
1990年代には、アドバイスが間違っていたでしょう。今日では、それは正しいです。
私は私が(多くのように)行う必要はありませんように、それは非常に便利なコードではnullチェックを変数にいくつかのデフォルトのデータを事前に割り当てることを見つけます。
私はいつもNULL_PTRで各変数を宣言するために提唱し、それぞれがいくつかの無効/デフォルト値をprimitivewith初期化されていないポインタによる非常に多くのバグを見てきています。
私はRTOSと高性能が、低リソースのシステム上で動作するので、我々が使用するコンパイラが未初期化の使用をキャッチしていない可能性があります。私は疑うけれども最近のコンパイラでも100%に頼っていたことができます。
は、マクロのは、広く使用されている大規模なプロジェクトでは、私もKloclwork / Purifyのは、未初期化の使用を見つけることができなかった稀なシナリオを見てきています。
だから私は、限り、あなたは、昔ながらのC / C ++を使用しているとして、それに固執言います。
ネットのような現代の言語はvaraiblesを初期化するために、保証、または初期化されていない変数の使用のためにコンパイルエラーを与えることができます。次のリンクパフォーマンス分析を行い、.NETの10〜20%のパフォーマンスヒットがあることを検証します。分析は非常に詳細であり、よく説明されています。
http://www.codeproject.com/KB/dotnet/DontInitializeVariables.aspx の