電子書籍の厳選無料作品が豊富!

C++ の new演算子について質問です。
new演算子を用いてクラスのインスタンスを作ったときに、
クラスのメンバー関数内で使用される自動変数はメモリの何処に割り付けられますか?

以下の回答の内のいずれかと想定しています。
・ヒープ領域
・スタック領域

たとえば、以下のように、クラスTestClassが定義されていたとします。

class TestClass {
int x;// int型(4byteとする)
char y;// char型(1byte)
long z;// long型(4byte)
void play(short);
}

void main(void){
TestClass* pt = new a();
play(10);

}

void TestClass:: play(short n){
char a;
long b;
staticc;

for(int a = 0; a < 10; a++ ){
b = n * a;
cout << b;
}
}


main関数内で、インスタンスを作成した時点で
・TestClassのデータメンバx,y,z ⇒ ヒープ領域に確保(4+1+4 = 9byte。もしかしたらアライメント     の関係でもう少し大きく領域を確保するかも)

・play関数で使われる変数n,a,bの領域は何処に確保されるのでしょうか?
変数cは静的変数用領域に保存される?

new演算子で作ったインスタンスはdelete演算子を使わないと消えないと勉強しました。(OSが消さない限り)
つまり、上記ではmain関数を抜けても、変数x,y,z,n,a,bの実体は残ると考えてよいのでしょうか?
そう考えると、n,a,bの実体はスタックではなく、ヒープ領域に確保する気がします、、

どうか、ご教授ください。

A 回答 (5件)

Cで書いたなら



struct TestClass {
int x;// int型(4byteとする)
char y;// char型(1byte)
long z;// long型(4byte)
}

void TestClass__play(struct TestClass * This, short n) ;

void main(void){
struct TestClass* pt = malloc(sizeof(struct TestCalss));
TestClass__play(pt,
10);

}

void TestClass__play(struct TestClass * This, short n){
char a;
long b;
static c;

for( a = 0; a < 10; a++ ){
b = n * a;
printf("%ld", b) ;
}
}

細かい違いはあるけど、あながちハズレではないはす。
こうすれでば、メンバ関数がどう実装されているか、メンバ関数で使用するローカル変数がどこに確保されるのが妥当か、わかるのではないでしょうか?

この回答への補足

お礼が大変遅くなりました。申し訳ありません。
おっしゃるとおり、メンバ関数で使用するローカル変数はスタックに詰まれると考えるのが妥当でした。

どうしても、自分の目で確かめたくなって、
Runesas製マイコンRX用の統合開発環境CubeSuite+でビルドをし、動かしながら、何処に領域を確保するのかを確認してみました。

結果、newしたオブジェクトもメンバ関数内のローカル変数の領域は、スタックに確保していました。
また、クラスのサイズをsizeof演算子で出したところ、以下のように面白い結果になりました。

1.メンバ変数をもつクラスのサイズ⇒メンバ変数の数×4byte
2.メンバ関数しかない(メンバ変数が無い)クラスのサイズ⇒1byte

1番は納得できますが、2番は何故1byteと思いました。
実際は、2番のケースでnewした際、1byte分ヒープ領域に確保するものの、中身は0のまま何も使用されていませんでした。

Tacosanさんのおっしゃる通り、処理系によって変わるので、これが全てではないでしょうが、大変勉強になりました。
ありがとうございました。

補足日時:2012/09/23 10:52
    • good
    • 0

>new演算子で、作ったインスタンスはどの時点で消えるのでしょうか?



delete演算子で消したとき。
またOSがインスタンスを削除することはありません。
正確にいえばインスタンスとして削除しないだけで、ヒープとしてはOSに帰りますが。

>「関数を抜けてしまえば不要になる」理由を教えて頂けないでしょうか。

関数内だけで使用する変数が関数抜けて必要になる場面てあるんですか?

この回答への補足

回答ありがとうございます。

> 関数内だけで使用する変数が関数抜けて必要になる場面てあるんですか?

大前提が頭から抜けていました。
おっしゃるとおり、自動変数のスコープは{}内ですね

> またOSがインスタンスを削除することはありません。
> 正確にいえばインスタンスとして削除しないだけで、ヒープとしてはOSに帰り> > ますが。
勉強になります。

補足日時:2012/09/09 14:53
    • good
    • 0

クラスのメンバー関数も、通常の関数も、同じ関数です。


メンバー変数が使えるとか言った機能以外の違いはありません。


ありがちな実装では

> ・TestClassのデータメンバx,y,z ⇒ ヒープ領域に確保(4+1+4 = 9byte。もしかしたらアライメントの関係でもう少し大きく領域を確保するかも)

メンバー関数へのポインタが加わるケースもあります。
決めつけないで、必要なときはsizeofで確認を。

> ・play関数で使われる変数n,a,bの領域は何処に確保されるのでしょうか?
> 変数cは静的変数用領域に保存される?

通常の関数と同じで
・引数はスタックに積まれる
・自動変数はスタック領域に確保される
・static変数はstaticな領域に確保される

この回答への補足

回答、ありがとうございます。

new演算子で、作ったインスタンスはどの時点で消えるのでしょうか?
上記の場合、main関数を抜けたときにポインタ変数ptが指しているオブジェクトは必ず消えるといえるでしょうか?

 消える場合 ⇒ C言語で使う関数と同様に考えれば良いので、
play関数内の自動変数a,bはスタックに確保されるかと思います。

 消えない場合 ⇒ もし、main関数を抜けてもオブジェクトは残るのであれば、
  play関数内の自動変数a,bは、後入れ先出しであるスタックではなく、
  ヒープ領域に確保するのではないかと考えております。

上記の場合、ポインタ変数が自動変数なので、
main関数を抜けたときに、オブジェクトも消してもらったほうが
安全だと思いました。

> メンバー関数へのポインタが加わるケースもあります。
> 決めつけないで、必要なときはsizeofで確認を。
コンパイラによって、変わってくるのですね。
勉強になりました。

補足日時:2012/09/08 10:13
    • good
    • 0

> クラスのメンバー関数内で使用される自動変数はメモリの何処に割り付けられますか?



ほとんどのコンパイラでは「スタック」に置かれます。
関数を抜けてしまえば不要になるので。

この回答への補足

早々の回答ありがとうございます。

「関数を抜けてしまえば不要になる」理由を教えて頂けないでしょうか。

補足日時:2012/09/08 10:16
    • good
    • 0

規格上何も決まっていません.

この回答への補足

早々の回答ありがとうございます。

補足日時:2012/09/08 10:13
    • good
    • 0

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!