Clojure在本地目录中找不到.clj ,.和CLASSPATH上的./classes

时间:2009-11-26 18:24:53

标签: macos clojure

当我评估(使用'hello)加载hello.clj时,REPL会抱怨以下错误:

java.io.FileNotFoundException: Could not locate hello__init.class or hello.clj on classpath:  (NO_SOURCE_FILE:0)

我正在调用这样的REPL:

java -cp "/Library/Java/Extensions/servlet-api-2.5-20081211.jar:... lots of jarfiles ...:/Library/Java/Extensions/clojure-contrib.jar:/Library/Java/Extensions/clojure-1.0.0.jar:./classes/:." jline.ConsoleRunner clojure.lang.Repl

阅读,看起来这个文件在PWD中找不到,但我补充道。走向没有成功的道路: - (。

在OS X 10.6上使用Java 1.6运行。

我确定我是个白痴,有人可以用LART打我吗?

编辑:我也尝试了ClojureX发行版,并得到了相同的结果。

5 个答案:

答案 0 :(得分:15)

如果hello.clj位于$DIR$DIR位于您的类路径上,则hello.clj需要以(ns hello)开头。如果它位于$DIR/$SUBDIR$DIR位于您的类路径中,则hello.clj需要以(ns $SUBDIR.hello)开头。通常,您的文件名结构和ns名称结构必须匹配,ns名称中的.替换为文件名分隔符,ns名称中的_ s对应的文件名中的任何- s。实际文件的名称必须是命名空间名称的最终组件(可能是唯一的组件,如果文件包含dir在类路径上)。

修改

一个扩展的例子。没有超出我上面所写的信息,所以如果这对你来说足够了,请跳过它;但是我知道在开始时让CP正确对我来说是非常痛苦的,所以我决定一步一步地把它写出来,这样某人,某个地方可能会幸免于那种特殊的“学习经历”;-)。

说这是你的命名空间定义:

;;; in file "hello.clj"
(ns hello)

(defn hello []
  (println "Hello!"))

然后,如果你把包含hello.clj的目录放在你的类路径上,你就可以了,REPL的(use 'hello)应该做你想做的事。

另一方面,如果你这样做:

;;; in file "hello.clj"
(ns my-namespace)
;;; ...

或者这个:

;;; in file "my-filename.clj"
(ns hello)
;;; ...

- 也就是说,如果您在文件名和命名空间名称之间引入不匹配,Clojure将无法找到您的命名空间。

此外,如果您将hello.clj放在/path/to/code中,但您在类路径上的内容实际上是/path/to,即/path/to/code的父目录,则需要执行此操作这样:

;;; in file "/path/to/code/hello.clj"
(ns code.hello)
;;; ...

然后你就可以(use 'code.hello)

最后,如果您调用文件my_namespace.clj,则需要致电ns my-namespace(反之亦然)。不应使用名称空间名称中的_和文件名中的-

答案 1 :(得分:3)

hello.clj是否包含(ns some-namespace)语句?如果是这样,那么在查找hello.clj之前,same_namespace会附加到CLASSPATH的每个元素上

答案 2 :(得分:2)

当我从repl工作并想加载文件时,我发现我必须首先调用类似的东西:

(add-classpath "file:///home/arthur/.../src/")
(add-classpath "file:///home/arthur/.../build/")

之前,repl可以在类路径中找到它们。 我将这些文件放在一个未包含在jar文件中的文件中,同时还有一个从其他文件重新加载所有内容的语句。当我构建一个jar文件时,我发现我不需要这样做。

答案 3 :(得分:1)

我已经定义了一个用于加载REPL的别名(在.bash_profile中):

alias clojure='CLASSPATH=$HOME/git/clojure/clojure.jar:$HOME/git/clojure-contrib/clojure-contrib.jar:.:classes rlwrap java clojure.lang.Repl'

答案 4 :(得分:1)

我的.emacs上有以下几行:

(setq swank-clojure-jar-path "~/src/clojure/clojure.jar"
      swank-clojure-extra-classpaths (append 
                      (directory-files "~/src/compojure/deps" t ".jar$")
                      (list
                       "~/src/swank-clojure/src/main/clojure"
                       "~/src/clojure-contrib/clojure-contrib.jar"
                       "~/src/clj/.")))

我加载位于〜/ src / clj的程序snake.clj并评估它(C-x h选择整个缓冲区,然后选择C-c C-c进行编译)。程序通过名称snake创建名称空间。现在,从emacs / slime,我做

(use 'snake)

就是这样。现在调用命名空间中定义的任何函数。

您的问题可能是您拥有hello.clj的目录可能不在您的类路径中。还要确保正确命名命名空间。如果在hello.clj中,你将你的名字空间命名为hello,那么你可以(使用'hello)。