実際、どちらのステートメントもヒープやスタックについて何も述べていません。コード
Object o;
コンテキストに応じて、次のいずれかを作成します。
- 自動ストレージを持つローカル変数、
- 名前空間またはファイル スコープの静的変数、
- 別のオブジェクトのサブオブジェクトを指定するメンバー変数。
これは、オブジェクトが定義されているコンテキストによって格納場所が決定されることを意味します。さらに、C++ 標準では、スタックストレージとヒープ ストレージについて言及していません。代わりに、 auto 、dynamic、staticまたはthread-local のいずれかであるstorage durationについて説明します。ただし、ほとんどの実装では、コール スタックによる自動ストレージと、ヒープによる動的ストレージが実装されています。
したがって、自動ストレージを持つローカル変数がスタック上に作成されます。静的 (およびスレッド ローカル) オブジェクトは通常、スタック上でもヒープ上でもなく、独自のメモリ領域に割り当てられます。また、メンバー変数は、それらが属するオブジェクトが割り当てられている場所に割り当てられます。それらには、それを含むオブジェクトの保存期間があります。
これを例で説明するには:
struct Foo {
Object o;
};
Foo foo;
int main() {
Foo f;
Foo* p = new Foo;
Foo* pf = &f;
}
オブジェクトFoo::o
(つまりo
、 class のオブジェクトのサブオブジェクトFoo
) はどこに作成されるのでしょうか? 場合によります:
foo.o
静的ストレージがあるためfoo
、静的ストレージを持ち、スタックにもヒープにも存在しません。
f.o
自動ストレージがあるため、自動ストレージf
があります(=スタックに存在します)。
p->o
動的ストレージがあるため、*p
動的ストレージがあります(=ヒープ上に存在します)。
pf->o
はを指しているf.o
ため、 と同じオブジェクトです。pf
f
実際、上記のp
との両方pf
に自動ストレージがあります。ポインターのストレージは、他のオブジェクトのストレージと区別がつかず、コンテキストによって決定されます。さらに、初期化式はポインター ストレージには影響しません。
ポインティー(= ポインターが指すもの) はまったく別の問題であり、あらゆる種類のストレージを参照できます:動的*p
であるのに対し、*pf
自動です。