2024 Clojure 状态调查! 中分享您的想法。

欢迎!请参阅 关于页面 了解更多关于其工作原理的信息。

+3
Documentation
编辑

hash-map 的文档说明该剧返回哈希映射。
然而,有一个不接受任何参数的arity,返回空的数组映射。

因此,文档和实现之间存在差异。

1 个答案

0

这里的困惑在于,“持久哈希映射”是这里的抽象,但有两种具体的实现:hash-map(PersistentHashMap)和array-map(PersistentArrayMap),后者根据映射大小转换为前者。

hash-map 是持久哈希映射抽象的构造器(通用),不保证返回的具体类型。《array-map》则是(显式地)数组映射的构造器。没有显式的PersistentHashMap构造函数。

我能够理解您说这里的抽象是“持久映射”。但是对于“持久哈希映射”就没有这么理解了。

是什么让数组映射成为一个哈希映射的实现呢?我在任何地方都没找到关于它的提及(参考文献明确将数组映射作为一个单独的事物提到),并且实现并没有使用任何哈希函数,这也是预期的。从概念上讲,数组映射与哈希映射的关系只有一点,那就是它们都是映射。

即使我避免查看调用任何此类映射的 `(type ...)` 的结果,还是会有一个与“哈希映射”这个词有关的期待——即会使用哈希函数。有人可能会说这根本不重要,我同意在大多数情况下确实如此,但是在调试与哈希和映射相关的内容时,这确实会造成混淆。

这更加令人困惑的是,尽管现在几乎可以视为常识,具有超过 8 项的映射字面量是哈希映射,但 `(hash-map 1 2)` 会返回一个哈希映射而不是数组映射。

还有其他的区别。至少,`print-dup` 在 `PersistentHashMap` 中定义了,但在 `PersistentArrayMap` 中没有定义,导致了类似于 `#=(clojure.lang.PersistentArrayMap/create {})` 这样意外的结果。
好吧,“持久映射”更公平一些,重要的类型是 IPersistentMap。

你是如何得到最后一个例子的?`pr` 或 `print` 都不会给你这个。
使用 `(binding [*print-dup* true] (prn {}))`。
...