Как вы используете тип за пределами своего собственного пространства имен в clojure?
У меня есть проект, созданный с лейнингом под названием techne. Я создал модуль под названием scrub с типом в нем Scrub и функцией foo.
Techne/scrub.clj:
(ns techne.scrub)
(deftype Scrub [state]
Object
(toString [this]
(str "SCRUB: " state)))
(defn foo
[item]
(Scrub. "foo")
"bar")
Techne/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)
Если я удаляю тестовый скраб, все работает нормально. Почему: использовать techne.scrub "импортировать" определения функций, но не определения типов? Как ссылаться на определения типов?
Ответы
Ответ 1
Поскольку deftype генерирует класс, вам, вероятно, потребуется импортировать этот класс Java в techne.scrub-test с помощью (: import [techne. scrub Scrub]) в вашем определении ns.
На самом деле я написал то же самое в отношении defrecord:
Еще одна вещь, которую вы могли бы сделать, - определить функцию-конструктор в scrub:
(defn new-scrub [state]
(Scrub. state))
и вам не нужно будет импортировать Scrub в тестовый скраб.
Ответ 2
Я добавляю импорт, но получаю ту же проблему. Я тестирую пакет 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]))
и вывод от leaine 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
Однако предложение использовать метод factory является жизнеспособным обходом.