在定义函数时Clojure中的^是什么?

时间:2018-01-06 14:55:45

标签: clojure

我是Clojure的新手,我在Clojure中被^搞砸了 我正在阅读Jepsen的clojure代码,用于测试分布式数据库的一致性。

您可以找到代码here。 在第50行中有一个 ^ MongoDatabase 。或者:

(defn ^MongoCollection collection
"Gets a Mongo collection from a DB."
[^MongoDatabase db collection-name]
(.getCollection db collection-name)) 

我不知道它是什么,因为^MongoDatabaseMongoCollection从未在此函数中使用过。

任何人都可以给我一些帮助。非常感谢。

3 个答案:

答案 0 :(得分:2)

在此上下文中,这是类型提示collection应该返回MongoCollection实例,而db arg应该是MongoDatabase实例。出于性能原因,这很有用,可以避免不必要的反射。

有关详情,请参阅this guide

  

^的另一个用途是提示类型。这些用于告诉编译器该值的类型,并允许它执行特定于类型的优化,从而可能使得结果代码更快:

答案 1 :(得分:1)

封面符号^在Clojure中用于两个目的。

第一个是类型提示。在声明函数时,您可以标记参数'类型或结果值如下:

(defn ^String concat-strings
  [^String a ^String b]
  (str a b))

类型提示可帮助编译器执行某些优化。

使用上限的第二个选项是在声明元数据时。元数据可以是布尔标志或地图。例如:

(def ^:private secret "test")

现在上面的变量被标记为私有,因此无法从其他名称空间中获取。

这是一个元地图用法示例:

(def ^{:private true
       :doc "My super secret password"
       :added "product-version"}
   secret
   "test")

让我们尝试阅读该变量的元数据:

(meta #'secret)

返回

{:private true,
 :doc "My super secret password",
 :added "product-version",
 :line 70,
 :column 7,
 :file "*cider-repl localhost*",
 :name secret,
 :ns #namespace[user]}

答案 2 :(得分:0)

另一点需要注意的是,类型提示可能具有欺骗性(即他们没有"执行"或"警告"实用程序):

implements Serializable

一般情况下,我会避免使用类型提示,因为它们很少需要(除非处理低级Java代码)。