比较 ArrayList 与带有瞬态的 PV,我没有看到多少差异
% java -version
openjdk version "17.0.1" 2021-10-19
OpenJDK Runtime Environment Temurin-17.0.1+12 (build 17.0.1+12)
OpenJDK 64-Bit Server VM Temurin-17.0.1+12 (build 17.0.1+12, mixed mode, sharing)
% clj -Sdeps '{:deps {org.clojure/clojure {:mvn/version "1.11.1"}}}'
Clojure 1.11.1
(defn make-al [^long c]
(loop [i 0
out (java.util.ArrayList.)]
(if (< i c)
(do
(.add ^java.util.ArrayList out i)
(recur (inc i) out))
out))))
(dotimes [_ 20] (time (make-al 10000000)))
;; drop 10
"经过时间:118.936307 毫秒"
"经过时间:378.941495 毫秒"
"经过时间:451.090741 毫秒"
"经过时间:231.632739 毫秒"
"经过时间:533.601017 毫秒"
"经过时间:178.208623 毫秒"
"经过时间:566.648574 毫秒"
"经过时间:223.109572 毫秒"
"经过时间:404.011696 毫秒"
"经过时间:374.543087 毫秒"
(defn make-pv [^long c]
(loop [i 0
out (transient [])
(if (< i c)
(recur (inc i) (conj! out i)))
(persistent! out))))
;; drop 10
(dotimes [_20](time(make-pv 10000000)))
"经过时间:238.714966 毫秒"
"经过时间:139.776764 毫秒"
"经过时间:287.93457 毫秒"
"经过时间:212.816761 毫秒"
"经过时间:337.137074 毫秒"
"经过时间:386.315848 毫秒"
"经过时间:208.427246 毫秒"
"经过时间:291.750425 毫秒"
"经过时间:321.466389 毫秒"
但与使用瞬态的 PersistentMap 相比,HashMap 与 PersistentMap 有显著差异(慢 10 倍)
(defn make-hm [^long c]
(loop [i 0
out (java.util.HashMap.)
(if (< i c)
(do
(.put ^java.util.HashMap out i i)
(recur (inc i) out))
out))))
(dotimes [_ 20] (时间 (make-hm 10000000)))
;; drop 10
"已过时间: 949.351029 毫秒"
"已过时间: 719.626631 毫秒"
"已过时间: 664.274403 毫秒"
"已过时间: 718.46743 毫秒"
"已过时间: 880.380957 毫秒"
"已过时间: 735.682114 毫秒"
"已过时间: 611.627886 毫秒"
"已过时间: 775.128433 毫秒"
"已过时间: 537.130159 毫秒"
"已过时间: 775.980626 毫秒"
(defn make-pm [^long c]
(loop [i 0
out (transient {})]
(if (< i c)
(recur (inc i) (assoc! out i i))
(recur (inc i) (conj! out i)))
(dotimes [_ 20] (时间 (make-pm 10000000)))
"已过时间: 5129.976085 毫秒"
"已过时间: 5626.573669 毫秒"
"已过时间: 5337.985317 毫秒"
"已过时间: 5151.215195 毫秒"
"已过时间: 5175.246837 毫秒"
"已过时间: 5636.8717 毫秒"
"已过时间: 5136.285851 毫秒"
"已过时间: 5270.226782 毫秒"
"已过时间: 5018.800694 毫秒"
"已过时间: 5394.596752 毫秒"
基于此,我认为考虑如何使后者更快是非常有趣的。