多くの言語では、ローカル変数は、それらが関数呼び出しを超えて生きなければならないので、それらが作成され、JavaScriptの/ PythonでGO - エスケープ解析
コールスタック、変数はヒープに配置されているだけ閉鎖に位置しています。 GOで
、(スライスタイプ[]int
など)いくつかのGOタイプのJavaScript/Pythonのような、メモリの他の部分を参照して行います。
GOでは、すべてのタイプの変数がJavascript/Pythonのように参照を保持するわけではありません。例えば
、
1)はCをより制御
ため、C構文&b[index]
を使用して、各アレイ素子の位置のアクセスを取得することを可能にする以外[3]int
型可変b
直接、Cのように、int
「sのアレイを記憶します 2)int
タイプ変数c
は、Cのように値がint
であることを直接的に格納します。ただし、Cは位置情報アクセスを取得するための構文(&c
)を提供することにより、 GOで
ローカル変数はヒープ/スタック上にあるため、私の理解では、ある(下記)のコード例では、コンパイラのエスケープ解析の適用に依存し、
func foo() []int {
// the array lives beyond the call to foo in which it is created
var a [5]int
return a[:] // range operator
}
ことをコンパイラに伝えています変数a
はスコープを超えているため、ヒープには割り当てますが、スタックには割り当てません。
質問:
は、変数はヒープに割り当てられますa
ていますか?
すべての言語がCのように動作するわけではないことに注意してください.JavaScriptやlispなどの多くの言語では、クロージャは実際にスタックの一部です。言語のスタックはCの意味では "スタック"に実装されていませんが、スタックはリンクされたリストとして実装されています。つまり、一部の言語のスタックがヒープに実装されています。 Javascriptの実装では、古典的な関数のリンクリストスタックや、囲まれたフリー変数を取り込むための何らかの種類のクロージャ発見メカニズムを実装することができます。どちらも同じように動作します。 – slebetman
ここでは、RubyのインタプリタをRubyに書く上で、関数型言語でのクロージャの伝統的な実装について説明しています。http://hokstad.com/how-to-implement-closures彼の説明 '伝統的なスタックの代わりに、ヒープ上の関数/メソッド呼び出しのアクティベーションフレーム(引数とローカル変数)をリンクリストとして置く - ヒープ内のインタープリタのスタックを実装している – slebetman