我在第49行开始的文件“constraint.clj”中有以下内容(用行号显示):
49 (defn stacker []
50 (let [s (first (.getStackTrace (new java.lang.Throwable)))]
51 {:name (.getMethodName s)
52 :file (.getFileName s)
53 :line (.getLineNumber s)}))
54
55 (def s (stacker))
从nrepl,我编译文件。当我检查s处的值时,它会显示。
app.constraint> s
{:name "invoke", :file "constraint.clj", :line 50}
所以,基本上,它似乎工作得很好,除了getMethodName不是我所期望的。我希望:name
为app.constraint/stacker
。我该怎么做?
答案 0 :(得分:2)
在内部,Clojure为每个与“namespace $ function-name”模式匹配的函数生成一个继承自clojure.lang.AFn
的Java类。执行函数时,将使用正确的arity在该对象上调用invoke方法。
您可以在此处找到来源:https://github.com/clojure/clojure/blob/master/src/jvm/clojure/lang/AFn.java
如果您想要原始方法,可以从Java堆栈跟踪中查看生成的类名。
(defn stacker []
(let [s (first (.getStackTrace (new java.lang.Throwable)))]
{:name (clojure.main/demunge (.getClassName s))
:file (.getFileName s)
:line (.getLineNumber s)}))
(stacker) ;=> {:name "app.constraint/stacker", :file "constraint.clj", :line 50}
此信息也可通过功能的元数据直接获得。
(meta #'stacker)