就像一个例子,函数内部put
创建x
属性及其全局值:
(defun foo ()
(put 'spam 'x 1))
(foo)
(get 'spam 'x) ; -> 1
是否可以在本地设置符号属性?
答案 0 :(得分:3)
不,因为'spam
始终是相同的符号,所以无法在本地设置属性。
我不知道这是否适合您的情况,但您可以创建一个新的符号并将属性放在上面。因为该功能以外的符号不可用。
(defun foo ()
(let ((private (make-symbol "private")))
(put private 'x 1)
(get private 'x)))
(foo) ;=> 1
(get 'private 'x) ;=> nil
make-symbol
返回“新分配的[和]未分隔符号”,这意味着(make-symbol "private")
返回的符号与全局'private
和其他所有符号不同。有关更多信息,请参阅here以了解有关创建和实习符号的Emacs手册部分。
Emacs也支持buffer-local variables,虽然这不是一回事(符号的值是特定缓冲区的本地值,但符号本身及其属性仍然是全局的。)
如果您只需要在本地将值绑定到名称,您也可以使用Emacs 24对lexical binding的支持,或者,如果您使用的是旧版本,则lexical-let
来自cl
1}}包(包含在Emacs中)。
答案 1 :(得分:2)
你可以在动态范围的意义上“本地”地做到这一点:
(require 'cl-lib)
(defun foo ()
(cl-letf (((get 'spam 'x) 1))
(get 'spam 'x)))
(foo) ; -> 1
(get 'spam 'x) ; -> nil
答案 2 :(得分:0)
虽然我不太明白你想做什么,但在我看来,你正在寻找一个闭包,即一个环境功能。为此,您必须启用词法绑定,从emacs 24.3 IIRC开始支持。要启用它,请将缓冲区局部变量lexical-binding设置为t。闭包的一个流行的例子是加法器工厂,这是一个函数,它返回一个常数加起来的函数。
(defun make-adder (constant)
(lambda (y) (+ y constant)))
(make-adder 3)
;; As you can see a closure is a function with an environment associated
=> (closure ((constant . 3) t) (y) (+ y constant))
(funcall (make-adder 3) 2)
=> 5
(funcall (make-adder 5) 2)
=> 8
所以是的,使用闭包你可以为函数设置私有变量。