【问题标题】:Clojure - problems with syntax for accessing gen-class from another namespaceClojure - 从另一个命名空间访问 gen-class 的语法问题
【发布时间】:2014-01-27 18:42:14
【问题描述】:

似乎 lein 重新编译代码的方式是不可预测的。我在一个目录中有一个 gen-class 文件,试图在另一个目录中访问它。例如,给定这个 gen-class:

(ns a.Target
    (:gen-class
     :state state
     :init  init
     :constructors {[String String] []}))

(defn -init
  [m1  m2]
  [[]  (atom {"A" m1 "B" m2})])

(defn -deref
  [this]
  @(.state this))

并尝试从另一个命名空间访问它,简化为尝试 1、2、3 的随机变化:

(ns b.runner
    (:require [a.Target  ] :as Target) ;1
    (:import '(a Target))              ;2
)

(compile 'a.Target) ;3

似乎没有可以识别“Target”而不是“a.Target”的语法,所以我处理 gen-class 的方式显然有些不正确。这是一个问题,因为我试图使用带注释的提供程序方法访问我们的 guice-injector,而注释语法似乎不接受完整或简单的类规范:

(definterface TargetProvider (^a.Target getTarget [this] ))
=> Exception in thread "main" java.lang.UnsupportedOperationException: nth not supported on this type:

或简化的:

(definterface TargetProvider (^Target getTarget [this] ))
=> Can't find class java.lang.Target

【问题讨论】:

  • 您的 ns 表单中有错字:(:require [a.Target :as Target]),而不是 (:require [a.Target ] :as Target)
  • 你到底想在这里实现什么?

标签: clojure clojure-java-interop


【解决方案1】:

ns 表达式应该是(ns b (:import a.Target)) 不需要使用:require 来导入类。由于ns 是宏,所以:require:use 和其他选项中的所有符号都不会被评估,因此无需引用它们。使用以下 ns 声明,您的 definterface 表达式应该可以工作。

(ns b
  (:import a.Target))

(definterface TargetProvider [^a.Target getTarget []])

(->> b.TargetProvider .getMethods seq)
;= (#<Method public abstract a.Target b.TargetProvider.getTarget()>)

编辑

这是使用上面定义的TargetProvider 接口的代理代码,我认为这是您在 cmets 中所要求的。

请注意,我还修改了接口getTarget 方法的声明,删除了this 参数,因为它实际上并没有接收到当前实例的引用。使用 proxy 时,有一个隐式绑定的 this 本地(有关详细信息,请参阅 here)。

(let [x (proxy [TargetProvider] []
          (getTarget [] (Target. "x" "y")))]
  (.getTarget x))

【讨论】:

  • 谢谢,这很有帮助。不想要求更多,但你能添加一个使用这个接口的代理的例子吗?当我添加该方法时,它似乎没有拾取注释。尝试例如( ^{提供 {}} ^a.Target getTarget [this] ( ... ))
  • 感谢您的编辑 - 非常感谢。但是,该语法给出:线程“main”中的异常java.lang.IllegalArgumentException:未找到匹配方法:clojure.lang.Reflector.invokeMatchingMethod(Reflector.java:53) 处的类的getMethod ...仍在使用语法,如果我能让这该死的东西工作,我会发帖的。
  • 我不确定您要实现什么,但您提到的错误听起来与语法无关。请添加导致您在上一条评论中发布的错误的整个 ns 的代码,我们将从那里获取它。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-08-06
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-04-06
相关资源
最近更新 更多