2011-02-09 37 views
0

に次のコードは有効ですか?言い換えればポインタの初期化クラス

class Foo() 
{ 
    int* Bar; 

    public: 

    Foo() 
    { 
     *Bar = 123; 
    } 
} 

値はコンストラクタでそのスペースに割り当てられる前に、Bar実際に実メモリ空間を指しているのだろうか?または、私は次のようなことをしていますか?

class Foo() 
{ 
    int* Bar; 

    public: 

    Foo() 
    { 
     Bar = new int[1]; 
     *Bar = 123; 
    } 

    ~Foo() 
    { 
     delete[] Bar; 
    } 
} 
+0

メモリアドレスを手作業で割り当てようとしていますか?いずれにせよ、私は専門家ではありませんが、私はあなたが '新しいint'、または他のプリミティブを言うことは決してないと確信しています。 – jakev

+0

Fitst oneが間違っています。あなたはそれを新しいものにする必要があります。 –

答えて

2

2番目の例のようにメモリを割り当てる必要があります。あなたが最初の例でコードを実行しようとした場合、それはあなたが初期化されていないBarポインタの値を指しているものは何でもメモリの一部に整数123を書こうとしているので、アクセス違反エラーで最も可能性の高いクラッシュします。

+0

これは例として提供されています。 – Maxpm

+0

[OK]を反映して私の答えを編集しました。 – Coincoin

2

あなたが動的配列をしたくない場合は、

Bar = new int; 
*Bar = 123; 

は十分です!そして、あなたはこれを行うにしました: - :次に

Bar = new int[5]; 
Bar[0] = 123; 
Bar[3] = 788; 
//etc 

delete Bar; //not delete[] Bar; 

あなたは(あなたが複数の値を格納できる使用して)動的配列をしたい場合は

をしかし、その後、これを行いますdelete[] Barは、割り当てられたメモリを削除する正しい方法です!

1

実際にバーはコンストラクタのスペースに値が割り当てられる前に実際のメモリ空間をポイントしますか?

号ポインタ単に「単純な」変数です。それはあなたのためのメモリを割り当てません。さらに、初期化しなければ、メモリ内の任意の、そしてほとんど予測できない場所を指し示します。

一般に、NULL(または好みに応じて0)に初期化するか、割り当てられたメモリに(Bar = new intと同じように)初期化する必要があります。最初の例で

1

- オブジェクトへ

int* Bar; 

ポインタポイント。コンパイラの仕事は整数ポインタBarにメモリ(すなわち、4バイト)を割り当てて、整数変数のアドレスを保持することである。ただし、参照先を指定する必要があります。

それは銀行があなたのアカウントを与えるより、のようなものです。銀行口座を持っていても、ATMからお金を引き出すことはできません。あなたのアカウントには引き分けるためのお金が必要です。お金がなければトランザクションは失敗し、プログラミングのパラダイムではその動作は未定義です。したがって、最初の例の動作は未定義です。私の類推があまりにも厄介であれば、私は残念です。第2の例で

-

ここ
int* Bar = new int[1] ; // Here [1] is unnecessary as your Bar points to a single integer memory location. 

Barは有効な整数の場所を指し示すポインタがフリーストアから得ています。だから、Barが指し示す場所にはゴミ値があるかもしれません。したがって、逆参照の前に、それを初期化してください。すなわち、

2番目の例では、リソースを管理しているので、ソースをフリーストアに戻す責任があります。