インタビューで質問があり、答えは「コンピュータのメモリ」でした。しかし、正確にはどこに..?それはランダムアクセスメモリですか、それともハードドライブですか?
5 に答える
彼らはおそらく「ヒープ」を探していました。これは、すべてのローカル変数、パラメーター、戻り値などが格納される「スタック」とは別のメモリ領域です。はい、それはすべてRAMにあり、ハードドライブにはありません。
動的に割り当てられるメモリは、一般に「ヒープ」と呼ばれるメモリから割り当てられます。
C ++には、実際には2つの「ヒープ」があります(技術的には同じ領域である場合とそうでない場合があると考えられます)。malloc()(およびファミリ)によって割り当てられたメモリは「ヒープ」から取得され、new(およびファミリ)によって割り当てられたメモリは「フリーストア」から取得されます。
「ヒープ」と「フリーストア」はどちらも、コンピュータサイエンスの「ヒープ」の特定のインスタンスのモニカであることに注意してください。
言語定義は、実装が定義するために残されている「ヒープ」または「フリーストア」が何を意味するかを定義しません。また、オペレーティングシステムは、メモリページに何が起こるかについての役割を果たしますが、それはほとんどのアプリケーションの範囲を超えています。
コンピュータサイエンスでは、「スタック」という用語は単純な教育ツールとして使用されます。これは、関数呼び出しを追跡するために使用されるメモリの領域を定義し、「ヒープ」とは異なります。最新のオペレーティングシステムでは、これは単純すぎる定義です。そのため、ランタイム「スタック」は通常「ヒープ」の一部として実装されるようになりました(これには、実行時にヒープ/スタックが衝突するかどうかを追跡する必要がないという利点があります。また、セキュリティ対策としても使用されます。スタックを壊して決定論的な結果を得るのが難しくなるにつれて)。
C ++標準では、演算子の新規または動的メモリ割り当てに関連して「ヒープ」という単語については言及されていません。したがって、おそらく一般的な用語である「ヒープ」は、自動変数のストレージ領域とは異なるメモリを示すために使用されます。
C ++標準は、脚注で次のように述べています。「C ++のメモリモデルは、ISO /IEC9899プログラミング言語Cのメモリモデルと互換性があることを目的としています。」
C標準を参照すると、「ヒープ」についても何も言及されていません。
したがって、要約すると、動的メモリ割り当ての実際のストレージは指定されていないと想定するのが最善です(整形式のプログラム構成と正しいデータの場合、実装によって異なります)。
最後にもう1つ。
4.「placementnew」はメモリを割り当てないことを覚えておくことが重要です。代わりに、事前に割り当てられたメモリ(引数として渡される)を使用してオブジェクトを構築します。
最新のPC、ワークステーション、またはサーバーマシンでは、「ランダムアクセスメモリですか、それともハードドライブですか?」に対する答えです。は:どちらでもない。仮想メモリに割り当てられます。最初に割り当てられたとき、与えられた仮想アドレスには物理的な存在がまったくない可能性があります。最初のアクセスでは、RAMで物理的にインスタンス化されますが、他の用途でRAMが必要な場合は、後でディスクまたは他のスワップデバイスのストレージに移動できます。その後アクセスを試みると、RAMに戻されます。
これは、仮想メモリの非常に基本的な説明です。本当に理解したい場合は、ウィキペディアまたはグーグルの記事を読んでください。
簡単に要約すると、一言で言えば「ヒープ」かもしれません。ただし、スタックまたはヒープと呼ばれるものは、コンテキストに依存することがわかります。例えば、
スタックについては、インテルプログラミングガイドのセクション6.2を参照してください。「SS」はスタックセグメントであり、連続したアドレス空間を提供します。関数を呼び出すと、その関数の差出人住所、渡されたパラメーター、およびローカル変数がこのセグメントに割り当てられます-「スタック」と呼ばれます。ポインタ変数(たとえばchar * p)がある場合、この変数はスタックに割り当てられますが、メモリはmalloc()またはCで呼び出されたときに割り当てられ、C ++はデータセグメント(DS)に割り当てられます)。また、スタンフォードのチュートリアルを参照してくださいしたがって、SSのスタックのトップをインクリメントして次のメモリアドレスに移動する代わりに、プロセッサはアドレス変換を実行する必要があります-アドレスがプロセスアドレス範囲内にあるかどうかを確認し、仮想アドレスをセグメント+に分割しますオフセット、特定のアドレスの値を取得します。
したがって、ここでの「スタック」と「ヒープ」の説明は、C、C ++などの言語を扱う場合、プロセッサアーキテクチャと密接に関連しています。
Javaの場合、すべてがヒープ上で実行されます。これは、すべてのJavaプロセスに共通のストレージ領域です。JVM仕様(セクション3.5および3.6を参照)では、各JVMスレッドには独自のプライベートスタックがあり、スタックフレームを格納します。渡されたパラメータ、ローカル変数など。最も重要なことは、これらのスタックフレームはヒープから割り当てることができ、順番にアドレス指定する必要がないことです。このJavaに加えて、Cのようなネイティブメソッドスタックも提供します。
しかし、私はインタビューの設定で推測しているので、「ヒープ」と言うのが最善かもしれません-そして、求められた場合にのみ詳しく説明することを考えてください。