Ole*_*Cat 3 compilation clojure
我已经建立了小项目:
project.clj:
(defproject testing-compilation "0.1.0-SNAPSHOT"
:dependencies [[org.clojure/clojure "1.8.0"]]
;; this is important!
:aot :all)
Run Code Online (Sandbox Code Playgroud)
SRC/core.clj
(ns testing-compilation.core)
(def x (do
(println "Print during compilation?")
1))
Run Code Online (Sandbox Code Playgroud)
然后,当我lein compile在项目目录中,我看到打印输出:
$ lein compile
Compiling testing-compilation.core
Print during compilation?
Run Code Online (Sandbox Code Playgroud)
我的问题是:为什么clojure在AOT编译期间评估顶级表单?它们不应该在程序启动时进行评估吗?
作为参考,Common Lisp默认不评估表单,并提供调整此行为的功能.Clojure中有类似的东西吗?如果没有,Clojure文档是否明确说明了这种行为?
UPD:表单也会在启动时进行评估.
指定主命名空间并编写打印的main函数后Hello, world!,我这样做了:
$ lein uberjar
Compiling testing-compilation.core
Print during compilation?
Created testing-compilation-0.1.0-SNAPSHOT.jar
Created testing-compilation-0.1.0-SNAPSHOT-standalone.jar
$ java -jar target/testing-compilation-0.1.0-SNAPSHOT-standalone.jar
Print during compilation?
Hello world!
Run Code Online (Sandbox Code Playgroud)
AOT过程的第一部分是找到包含主命名空间的文件,并通过从上到下评估每个表达式来加载它.
其中一些表达式将是require加载其他名称空间的表达式,这些名称空间递归加载更多名称空间.
其他将是defn具有启动编译器和生成类文件的效果的表达式.为每个函数生成一个类文件.
其他表达式可能会进行一些计算,然后执行生成类文件的操作,因此让它们有机会运行是很重要的.这是一个组成的例子:
user> (let [precomputed-value (reduce + (range 5))]
(defn funfunfun [x]
(+ x precomputed-value)))
#'user/funfunfun
user> (funfunfun 4)
14
Run Code Online (Sandbox Code Playgroud)
可以设计一个不会在开始时评估顶级表单的lisp,或者如您所述,使其成为可选项.在Clojure的情况下,决定在AOT和"非AOT"加载中保持单一的评估策略,因此程序总是运行相同,无论它们如何编译.这些是他人做出的个人设计选择,所以我不能在这里说出他们的动机.
| 归档时间: |
|
| 查看次数: |
280 次 |
| 最近记录: |