`symbol-value`は何をしますか?


13

ドキュメントは私を賢くしませんでした:

この関数は、シンボルの値セルに格納されている値を返します。これは、変数の現在の(動的な)値が格納される場所です。変数にローカルバインディングがない場合、これは単にグローバル値です。変数がvoidの場合、void-variableエラーが通知されます。

symbol-valueのポイントは何ですか?どこでいつ使用する必要がありますか?


3
Emacsに尋ねて答えを見つけてくれてありがとう。それが正しいアプローチです。最初にEmacsに質問し、それからまだ不明な点について質問してください。あなたの質問であなたがすでに試したことを教えてください。称賛!
ドリュー

回答:


13

Elispコードで、シンボルの値、つまり変数と見なされるときの値を取得する場合に必要です。

Elispシンボルには、いくつかの特性/機能があることに注意してください。

  • 名前があります(関数symbol-nameが与える)
  • 変数と見なされると、値を持つ場合があります(これsymbol-valueにより)
  • 関数と見なされると、関数に名前を付ける場合があります(これsymbol-functionにより)
  • プロパティリストがあります(これsymbol-plistにより)

シンボルは、さまざまな属性を持つオブジェクトとして考えてください。


1
(ドキュメントが示すように)symbol-value常にシンボルの動的バインディングを返すことにも注意してください。この方法で字句の値を取得することはできません。
phils

2
C-h i g (elisp) Symbol Components RETこれらのさまざまなシンボルセル/コンポーネントのドキュメントも参照してください。
phils

@phils:うーん、私は疑問に思う:(setq lexical-binding t) (let ((v 42)) (message "lex: %S, val: %S" lexical-binding (symbol-value 'v)))。しかし、はい、それは(のelisp)で言っていることですLexical Binding:「機能のようなsymbol-valueboundp'set'だけ取得したり、バインディング変数の動的な変更を(すなわち、そのシンボルの値セルの内容)」。しかし、それについては何も言われていませんSymbol Components
ドリュー

10

(Doh、@ Drewはすでに以下のいくつかを挙げています。とにかく、ここに追加の詳細があります。)

シンボルコンポーネントのマニュアルページで説明しているように、各シンボルには、印刷名セル、値セル、関数定義、プロパティリストの4つのコンポーネント(セル)があります。値セルまたは関数セルのいずれかが無効になり、プロパティリストがnilになる場合があります。

マニュアルでも指摘しているように:

各シンボルには個別の値と関数のセルがあるため、変数名と関数名は競合しません。

それがあなたが持つことができる理由です、例えば:

(setq test "kittens")
(defun test ()
  (message "puppies"))
(symbol-value 'test)    ; => "kittens"
(symbol-function 'test) ; => (lambda nil (message "puppies"))

1
ああ、機能とは対照的に価値があるので、理解しやすくなっています。ありがとう。
不愉快な猫

8

少し歴史的な参考文献があります(説明したイベントが起こったときはまだ生まれていませんので、もっと知識のある誰かが私を修正するかもしれません。これはすべて古い記事や本を読んでいるからです)。

免責事項を省いた後、FortranとLispの時代には「シンボリック」は「オブジェクト指向」が今日のように一種の流行語だったようです。すなわち、プログラムは通常、数字が最終的に差し込まれ、数字のプレースホルダーが重要ではない単なる巨大な数式と見なされていました。プログラムに含まれるすべての記号情報は、そのプログラムが実行、コンパイル、または解釈されるとすぐに消えます。Lispの目新しさは、プログラムが実行、コンパイル、または解釈された後でも、シンボルをプログラム内に保持できることでした。これは、「シンボリック代数」(直接計算ではなく紙/黒板で行われる代数式の操作など)などの用語に影響を与えました。この(および他の記号的なもの)をサポートするために、記号には名前といくつかのプロパティを装備する必要がありました。非シンボリックの観点からは、「シンボルは単なる名前付きポインター」であると言うかもしれません。これは真実ではありませんが、構造体へのポインターのようなものであれば、実際にはシンボルは左の指示子です可変値ペアの手側。これにより、symbol-value 非記号言語でのポインターの逆参照として機能します。

現代のLispは、1つのシンボルに関連付けることができる値の数が異なります(複数のメモリスタック/ヒープを持つ非シンボリック言語がある場合、異なるスタックのコンテキストで解釈されたときに同じポインタが意味を持つ状況を想像できます/ヒープ)。したがって、Lisp2言語(Emacs Lispはそのような言語の1つです)には、関数と変数用の別個のストレージがあります。これがsymbol-function、「関数ストレージを指すポインターを逆参照する」という理由もあります。Schemeにはこの特別なストレージとClojure AFAIKはありませんsymbol-plist


7

小さなデモ:

(setq v1 10)
;;10
v1
;;10
(setq v2 'v1)
;;v1
v2
;;v1
(symbol-value v2)
;;10 
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.