gpt4 book ai didi

clojure - Clojure 中函数名前面的 -(减号)符号是什么意思?

转载 作者:行者123 更新时间:2023-12-04 22:54:24 26 4
gpt4 key购买 nike

我无法理解以下内容。在 Clojure 中定义 main 函数时(基于 Leinigen 生成的代码),有一个 -函数名前的符号main .

我访问了 clojure.com 上的原始文档,发现 defndefn-除其他外,请参阅 https://clojuredocs.org/search?q=defn .我也在谷歌上搜索,发现一个来源说 -在 main 前面表示该函数是静态的( http://ben.vandgrift.com/2013/03/13/clojure-hello-world.html )。
-真的意味着该功能是静态的吗?我找不到任何其他证实这一点的消息来源。我也可以同时使用 (main)(-main)调用main方法时没有任何问题。

鉴于以下代码...

(defn -main
"I don't do a whole lot ... yet."
[& args]
(println "Hello, World!"))

(defn main
"I don't do a whole lot ... yet."
[& args]
(println "Hello, World!"))

我得到以下输出...
(main)
Hello, World!
=> nil
(-main)
Hello, World!
=> nil
Loading src/clojure_example/core.clj... done
(main)
Hello, World!
=> nil
(-main)
Hello, World!
=> nil

我注意到没有区别。两个函数的输出相同。任何帮助表示赞赏!

最佳答案

首先,一个旁白。

关于宏defn对比 defn- ,第二种形式只是“私有(private)”功能的简写。长格式如下所示:

(defn ^:private foo [args] ...)

但是,这只是对用户的一个提示,即不应使用这些功能。测试等很容易解决这个弱“私有(private)”限制。由于麻烦,我从不使用所谓的“私有(private)”函数(我有时会使用元数据 ^:no-doc 和像 foo-impl 这样的名称来表示 fn 不是面向公众的 API 的一部分,图书馆用户应该忽略)。

Clojure 程序中的“main”函数

在 Java , 程序总是通过调用选定类中的“main”函数来启动
class Foo
public static void main( String[] args ) {
...
}
}

进而
> javac Foo.java   ; compile class Foo
> java Foo ; run at entrypoint Foo.main()

Clojure 选择将初始函数命名为 -main .函数名中的连字符 -main并不是很特别,只是它使名称不寻常,因此不太可能与代码库中的任何其他函数发生冲突。您可以 see this in the definition函数的 clojure.main/main-opt .

你可以看到hypen约定的部分起源 in the docs for gen-class (向下滚动查看有关 :prefix 的部分)。请注意,如果使用 gen-class,则使用连字符是可以更改的。用于 java 互操作。

使用 the Clojure Deps & CLI tools , 名称 -main假定为程序的起点。

如果您使用 Leiningen,它会更加灵活,并允许覆盖 -main程序的入口点。

在 Leiningen 项目中,如下所示的条目指示当您键入 lein run 时从何处开始:
; assumes a `-main` function exists in the namespace `demo.core` 
:main ^:skip-aot demo.core

所以在这样的程序中:
(ns demo.core )

(defn foo [& args]
(newline)
(println "*** Running in foo program ***")
(newline))

(defn -main [& args]
(newline)
(println "*** Running in main program ***")
(newline))

我们得到了正常的行为:
~/expr/demo > lein run

*** Running in main program ***

但是,我们可以通过另一种方式调用该程序:
> lein run -m demo.core/foo

*** Running in foo program ***

制作 foo发挥“入口点”的作用。我们还可以更改 :main像这样设置:
:main ^:skip-aot demo.core/foo

并获得行为:
~/expr/demo > lein run

*** Running in foo program ***

因此,拥有一个名为 -main 的 Clojure 程序的初始函数是默认设置,并且是大多数工具所必需的。如果使用 Leiningen,您可以覆盖默认值,尽管这可能仅在测试和开发中有用。

请记住,每个命名空间都可以有自己的 -main函数,因此您只需更改调用的初始命名空间即可轻松更改初始函数。

最后, -main 中的连字符us 与用于通过 defn- 定义的伪私有(private)函数的连字符无关.

关于clojure - Clojure 中函数名前面的 -(减号)符号是什么意思?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58559944/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com