【问题标题】:Clojure static typing, part 2Clojure 静态类型,第 2 部分
【发布时间】:2010-11-17 13:07:18
【问题描述】:

这是 my previous question 关于 Clojure 静态类型的后续内容。

我浏览了编译器的Java源代码,有几个地方检查*warn-on-reflection*的值,但是当我编译以下代码时,我只得到一个运行时错误:

(defn div-2 [^String s] (/ 2 s))

在任何情况下,这段代码应该给出编译时警告(它没有)?让编译器对以下代码发出警告有多难:

(defn get-length [^String s] (.length s))
(defn test-get-length [] (get-length 2.0))

谢谢。

【问题讨论】:

    标签: clojure static-typing


    【解决方案1】:

    问题是编译器不跟踪def'd 变量的类型。所以是的,在你的简单例子中,这是可能的。但是你多久传递一次文字?很少,在一个真正的程序中。

    让类型像在真正的静态类型语言中那样“流过”需要大量的返工。您必须通过 var、动态反弹 var、取消引用等来跟踪类型信息。然后您仍然遇到将项目从集合/序列中拉出的问题,这意味着泛型类型,这是巨大的一罐蠕虫......

    Clojure 中的类型注解从未打算在编译时提供类型安全 - 它们只是允许编译器生成更优化的代码(如果遇到意外类型,则会以运行时错误为代价。)

    使用完整的静态类型信息来检测编译器可能是可能的,但此时您已经在很大程度上重写了语言,并且您必须在如何处理类型方面做出许多决定和权衡。它真的不再是 Clojure 了。

    【讨论】:

    • 是否可以使用语言结构的元数据来对它们进行一些静态类型检查而不从根本上修改语言?
    【解决方案2】:

    与其尝试修改编译器,为什么不编写一个单独的工具来扫描 Clojure 代码文件并警告类型违规?您可以开发自己的类型表示法,使用只是折叠成普通的无类型 Clojure 代码的宏。但是当您运行静态类型检查器时,它会识别类型并输出警告。

    如果您准备迎接稍微大一点的挑战,您甚至可以让它执行类型推断,从而减轻符号的负担。

    【讨论】:

    • 类型推断并不难,但您必须知道所有库/预定义或导入函数的类型。
    • @jayunit100 由于 lisp 代码只是 s 表达式,它们可以被 lisp 阅读器读取。您甚至可以遍历宏扩展代码。 Common Lisp 有一些不同的代码漫游器,对于 Clojure 则不确定。其中一个可能会被强制执行任务。
    【解决方案3】:

    在该线程之后,现在有一个项目旨在将渐进式输入引入 clojure(如 Dart 等)。值得测试: Typed-Clojure

    如果有人在实际使用后也能给出一些反馈……

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-06-26
      • 1970-01-01
      • 1970-01-01
      • 2017-12-27
      • 2018-08-10
      • 1970-01-01
      相关资源
      最近更新 更多