Clojure变量与其他语言中的指针/引用的区别

5

我正在尝试理解Clojure中的Var概念。

据我所知,它只是一个指向值的引用/指针。一个Var的“根值”可以被视为线程上指向的初始值。此外,我认为——在幕后——每个Var都有一个地址,指向它所指向的内存位置(尽管像Java、Javascript这样的语言不会给你访问该特定位置的权限,而且可能会进行一些幕后操作,使该地址不稳定)。

问题:这种思考方式正确吗?以哪些方式将Clojure Var视为引用/指向值是错误的?

给定以下内容:

(def v 7)

说"Var #'v指向值7"这样的话是否恰当?


这里有一个相当不错的总结:http://www.braveclojure.com/zombie-metaphysics/ - jmargolisvt
还不错:http://gfredericks.com/speaking/2015-02-25-vars.pdf - ClojureMostly
1个回答

7
是的,这是一个很好的概念。我会稍微调整你的最后一句话: #'v 扩展为 (var v),说 var (var v) 没有意义,应该只说 var v。此外,我会说 derefs 为值 7 而不是指向。是的,它们的行为类似于指针,但它们有一个特殊的 deref(或 @)形式来解除引用它们(并且您不能进行指针算术运算)。
我认为采用术语 deref 对于理解 Clojure 的另一个方面非常重要:当您使用任何符号时,例如我们进行函数调用 (inc 1),实际上存在一个隐藏的步骤! inc 是与变量 inc 关联的符号(inc 实际上不是一个函数!inc 只是解除引用到一个函数),但然后评估变量自动解除引用。当您编写(var inc)时,实际上只是防止了那个 deref。这就是为什么当您更改或替换变量时,例如我们重新定义 inc,新代码会被执行。
重点是,在考虑指针方面时,您可能会想将 inc 视为某个变量指向的函数。这是不正确的。inc 是与解除引用到函数的变量相关联的符号。在使用 var inc 时,它自动解析为函数以方便使用。从这个意义上说,你可以认为只说 v 解除引用到值 7 是准确的。v 是一个变量,您实际上不需要指定它。(显然,当您试图明确指出它是一个变量时,称其为变量也没有错)。

1
你必须使用alter-var-root来设置它们是错误的,你可以使用interndef,还有其他可能的方法来设置变量。 - noisesmith
哎呀!感谢您的纠正。我已删除了错误的陈述。如果仍然不太正确,请直接编辑答案。我认为添加关于alter-var-root、def和intern的解释会很有用。再次感谢您指出错误,我已删除了以前的评论,因为它是错误的,我不想让回答的读者分心。 - Timothy Pratley

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接