2009-06-11 5 views
2

現在、C++コースを受講しており、全体を深く理解しようとしています。 私はいくつかの理論を思い付いた誰かがそれらを確認することができれば、それは素晴らしいことだ:変数の初期化とコンストラクタ

すべての変数(ローカル、グローバル、staic、メンバーと非会員)はそのctorのは

最初に使用する前に呼び出されることが保証されます

intのようなプリミティブのctorsは基本的にno-opsなので、明示的に値を割り当てています。デフォルトのゼロ値はありません。

以下のクラスは、意味的に同一である(同一のコードを生成すべきである)

class A 
{ 
    int n; 
}; 

class A 
{ 
    int n; 
public: 
    A() : n() {} 
}; 

class A 
{ 
    int n; 
public: 
    A() { n = int(); } 
}; 

変数nは、依然としてすべての場合に初期化されていません。

EDIT:

私がabsolutetlyこの主題の複雑さを過小評価し、私の仮定のほとんどが間違っていたように思えます。現在、Iamはオブジェクトの初期化の基本的なルールを見つけようとしています。

答えて

3

あなたはthis面白いかもしれません。

新しいfooと新しい はFoo()との違いは、前者初期化されていない なり、後者がfoo がPOD型である場合 デフォルト(ゼロに)初期化されることです。括弧、部材「」 「は」常に

+1

このステートメントは信じがたいものです。 class Bar {int n; }は暗黙的に定義されたctor is/trivial /(ISOの正式な用語)であるため、PODです。しかし、それは存在し、 'new Bar;と' new Bar() 'の両方がそれを呼び出します。どちらの場合も、Bar :: n()はBar :: nを初期化します。 – MSalters

+0

"class B {int n;};" PODにはプライベート非静的メンバー 'n'が含まれているため、* PODではありません。しかし、それが "class B {public:int n;};"それはPODなので、 "new Bar()"を実行すると、 'n'は値で初期化されます。 –

+1

初心者がこのテーマを完全に理解することは可能でしょうか?あまりにも多くのルールと例外があるようです:-( – codymanix

4

私はあなたが間違っていると思います。あなたが言うとき:

int n = int(); 

その後、n(および他のすべてのPODタイプ)は0に初期化されます。

また、あなたが初期化と代入の違いについてあなたの心の中で非常に明確であることを確認してください - これはC++で非常に重要である:

int n = int(); // initialisation 
n = 0;   // assignment 
1

ありません0に初期化されますが、 括弧で、ゴミを含めることができると フォームを使用していないときに、変数だけです最初のケースでは初期化されずに残った。

ユーザー定義のコンストラクタを持つクラスのメンバの場合、状況は単純です。コンストラクタは常に呼び出されます。

最初の例のように、組み込み型(および 'plain old data'構造体)は初期化されずに残ることがあります。彼らはユーザが提供するコンストラクタを持っていませんが、構文(他の2つの例)を使用すると、ゼロに初期化されます。

このややトリッキーなルールの理由は、過度のオーバーヘッドを避けるためです。あなたが定義されている場合、たとえば:

struct S 
{ 
    int array[1024*1024]; 
}; 

をあなたがそれらを必要に応じて値のみを割り当てることを意図して、あなたは1を構築するたびに、コンパイラがゼロでメモリ4MBのをごまかしたくないでしょう。

+0

これは私が思っていたよりもはるかに複雑です、私は空のctor A(){}を作成すると、変数nが初期化されます!あなたは空のctorを持っていません。ctorを持たないのと同じです(暗黙のうちにデフォルトのctorが作成される)ので、私の第1クラスと第4クラスは同じでなければなりませんが、そうではありません – codymanix

+0

これは間違っています。私はスタックやヒープ上にあると仮定しています静的なオブジェクトの場合、メンバーはコンストラクターが呼び出される前にゼロに初期化されます(これは ' –

1
class A 
{ 
    int n; 
}; 

メモリのみが割り当てられ、nの初期化は行われません。ここn


class A 
{ 
    int n; 
public: 
    A() : n() {} 
}; 

は次いでint()があると一時INTを引き起こす 最初の(任意のデフォルト値なし)に構成されている。ここで0


class A 
{ 
    int n; 
public: 
    A() { n = int(); } 
}; 

n、で初期化されます値0で作成 これはに割り当てられます;

+0

非常に奇妙なことに、A()の2番目のバージョンがあると確信していました。n(){}はプロジェクトの中でnを初期化しないようにしました私はGCCを使用しましたが、これはコンパイラに依存することができますか? – codymanix

+0

@ codymanix。これは標準的な動作ではありません。私は標準の最初のバージョンを信じていますが、これは誰がそのようなことを行うのだろうと指定されていませんでした!だからあなたの観察は非常に古いコンパイラにも当てはまるかもしれません。 –

関連する問題