13

我有一个名为 techne 的 leiningen 项目。我创建了一个名为 Scrub 的模块,其中有一个名为 Scrub 的类型和一个名为 foo 的函数。

技术/scrub.clj:

(ns techne.scrub)
  (deftype Scrub [state]
    Object
     (toString [this]
     (str "SCRUB: " state)))

(defn foo
  [item]
  (Scrub. "foo")
  "bar")

技术/scrub_test.clj:

(ns techne.scrub-test                                                                                                                                             
  (:use [techne.scrub] :reload-all)                                                                                                                               
  (:use [clojure.test]))                                                                                                                                          


(deftest test-foo                                                                                                                                                 
  (is (= "bar" (foo "foo"))))                                                                                                                                                           

(deftest test-scrub                                                                                                                                               
  (is (= (Scrub. :a) (Scrub. :a)))) 

当我运行测试时,我收到错误:

Exception in thread "main" java.lang.IllegalArgumentException: Unable to resolve    classname: Scrub (scrub_test.clj:11)
    at clojure.lang.Compiler.analyzeSeq(Compiler.java:5376)
    at clojure.lang.Compiler.analyze(Compiler.java:5190)
    at clojure.lang.Compiler.analyzeSeq(Compiler.java:5357)

如果我删除测试擦洗一切正常。为什么 :use techne.scrub “导入”函数定义而不是类型定义?如何引用类型定义?

4

2 回答 2

16

因为deftype生成一个类,您可能需要在您的 ns 定义中使用 (:import [techne.scrub Scrub]) 在 techne.scrub-test 中导入该 Java 类。

实际上,我在这里就 defrecord 写了同样的事情:

你可以做的另一件事是在scrub中定义一个构造函数:

(defn new-scrub [state] 
  (Scrub. state))

然后你就不需要在 test-scrub 中导入 Scrub。

于 2010-09-11T12:42:35.150 回答
1

我添加了导入,但遇到了同样的问题。我正在使用 Expectations 包 2.0.9 进行测试,尝试导入 deftype Node 和接口 INode。

在 core.clj 中:

(ns linked-list.core)

(definterface INode
  (getCar [])
  (getCdr [])
  (setCar [x])
  (setCdr [x]))

(deftype Node [^:volatile-mutable car ^:volatile-mutable cdr]
  INode
  (getCar[_] car)
  (getCdr[_] cdr)
  (setCar[_ x] (set! car x) _)
  (setCdr[_ x] (set! cdr x) _))

在 core_test.clj 中:

(ns linked-list.core-test
  (:require [expectations :refer :all]
            [linked-list.core :refer :all])
  (:import [linked-list.core INode]
           [linked-list.core Node]))

以及 lein autoexpect 的输出:

*************** Running tests ***************
Error refreshing environment: java.lang.ClassNotFoundException: linked-list.core.INode, compiling:(linked_list/core_test.clj:1:1)
Tests completed at 07:29:36.252

然而,使用工厂方法的建议是一种可行的解决方法。

于 2014-12-30T12:33:29.080 回答