【问题标题】:How to nicely call other JVM languages from clojure?如何从 clojure 中很好地调用其他 JVM 语言?
【发布时间】:2012-08-21 10:35:44
【问题描述】:

有时您想粘合用不同 JVM 语言编写的解决方案。为此,您需要调用该语言或以某种方式使用 java bitcodes。在 Clojure 中,最纯粹、最安全、最好的方法是什么?

例如,从 Clojure 调用 Scala 的最佳方法是什么?

(我知道其他方式很简单。您可以按照Can you mix the JVM languages? ie: Groovy & Clojure 中所写的方式通过 gen-class 生成 .class,但这仅允许您使用其他语言的 clojure。)

【问题讨论】:

  • 没有任何best way,一切都取决于context

标签: clojure


【解决方案1】:

由于 Clojure 在 JVM 上运行,因此您可以访问 Clojure 之外的类路径上的任何已知类。这是一个 Scala 示例。为了使类路径设置和依赖管理更容易,请使用 Leiningen 生成项目。

lein new clojure-scala

在项目文件夹中,修改project.clj并添加Scala语言库的依赖,并将scala-src文件夹添加到类路径中:

(defproject clj-scala "0.1.0-SNAPSHOT"
  :description "FIXME: write description"
  :url "http://example.com/FIXME"
  :license {:name "Eclipse Public License"
            :url "http://www.eclipse.org/legal/epl-v10.html"}
  :dependencies [[org.clojure/clojure "1.3.0"]
                 [org.scala-lang/scala-library "2.7.1"]]
  :compile-path "scala-src" )

创建目录 scala-src,并在该文件夹中创建以下 Scala 类:

class HelloWorld {
  def sayHelloToClojure(msg: String) =
    "Here's the echo message from Scala: " concat msg
}

使用 scalac 编译类。现在运行 lein deps 以下载依赖项。通过运行 lein repl 启动 Clojure REPL。您可以导入 Scala 类,对其进行实例化并调用 sayHelloToClojure 方法。

user=> (import HelloWorld)
HelloWorld
user=> (.sayHelloToClojure (HelloWorld.) "Hi there")
"Here's the echo message from Scala: Hi there"

这与您使用 Scala 类和 Java 代码的方式兼容。这可能会很棘手,引用Frequently Asked Questions - Java Interoperability:

使用 Java 中的 Scala 类可能会很棘手,尤其是如果您的 Scala 类使用高级特性,如泛型、多态方法、 或抽象类型。由于Java没有这样的语言特性,你 必须对Scala类的编码方案有所了解。

【讨论】:

  • 如果您正在寻找一种从 Clojure 中以交互方式评估 Scala 的方法——通过嵌入 Scala 环境——这在技术上可能是可行的;但即使在这种情况下,Scala 也必须编译和加载一个类。
  • 使用 Scala lang 依赖项,因为当 Scala 库不在类路径中时,Java - 因此 Clojure - 无法实例化 Scala 类。
【解决方案2】:

从 Clojure 调用其他 JVM 语言非常容易 - 您需要做的就是使用 Java interop 语法。

例子:

;; import Java classes
(ns my-ns
  (:import [some.package ClassOne ClassTwo ClassThree]))

;; call a regular method on an object
(.method someObject arg1 arg2)

;; call a constructor
(ObjectToConstuct. arg1 arg2)

;; call a static method
(Math/floor 2.3)

;; Use a static field
(+ 2 Math/PI)

基本上,使用这些技术,您可以调用任何其他创建 JVM 类的语言(包括 Java、Scala 和可能大多数其他 JVM 语言)

【讨论】:

    猜你喜欢
    • 2018-10-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-06-02
    • 1970-01-01
    • 2013-04-06
    • 2010-10-10
    • 2013-01-05
    相关资源
    最近更新 更多