Clojure 中的 let 与 def
我想在 clojure 程序中创建 Java Scanner
类的本地实例。 为什么这不起作用:
; gives me: count not supported on this type: Symbol
(let s (new Scanner "a b c"))
但它会让我创建一个像这样的全局实例:
(def s (new Scanner "a b c"))
我的印象是唯一的区别是范围,但显然不是。 let
和 def
有什么区别?
I want to make a local instance of a Java Scanner
class in a clojure program. Why does this not work:
; gives me: count not supported on this type: Symbol
(let s (new Scanner "a b c"))
but it will let me create a global instance like this:
(def s (new Scanner "a b c"))
I was under the impression that the only difference was scope, but apparently not. What is the difference between let
and def
?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(6)
问题是您使用
let
是错误的。let
的工作方式如下:因此,您的示例应该如下所示:
您只能在 let 范围内使用由 let 进行的词法绑定(左括号和右括号)。 让我们创建一组词法绑定。 我使用 def 来进行全局绑定,并使用 let 来绑定我只想要在 let 范围内的东西,因为它可以保持事物的干净。 它们都有各自的用途。
注意: (Class.) 与 (new Class) 相同,它只是语法糖。
The problem is that your use of
let
is wrong.let
works like this:So your example should be something like this:
You can only use the lexical bindings made with let within the scope of let (the opening and closing parens). Let just creates a set of lexical bindings. I use def for making a global binding and lets for binding something I want only in the scope of the let as it keeps things clean. They both have their uses.
NOTE: (Class.) is the same as (new Class), it's just syntactic sugar.
LET 不是“在当前范围内创建词法绑定”,而是“使用以下绑定创建新的词法范围”。
LET is not "make a lexical binding in the current scope", but "make a new lexical scope with the following bindings".
简化:def用于全局常量,let用于局部变量。
Simplified: def is for global constants, let is for local variables.
正确的语法:
Correct syntax:
即使含义相关,它们的语法也不同。
let 接受一个绑定列表(名称值对),后跟要在这些绑定的上下文中计算的表达式。
def 只接受一个绑定,而不是一个列表,并将其添加到全局上下文中。
The syntax for them is different, even if the meanings are related.
let takes a list of bindings (name value pairs) followed by expressions to evaluate in the context of those binding.
def just takes one binding, not a list, and adds it to the global context.
您可以将
let
视为使用fn
创建新词法范围的语法糖,然后立即应用它:因此您可以使用简单的代码实现
let
宏和fn
:You could think of
let
as syntactic sugar for creating a new lexical scope withfn
then applying it immediately:So you could implement
let
with a simple macro andfn
: