icy*_*com 4 clojure clojurescript
我有一张简单的地图:
(def my-map
{[1 2 3] 1
[1 2 4] 5
[3 4 2] 3
[4 5 3] 3
[5 2 5] 6
[9 2 1] 5
[8 3 1] 6})
Run Code Online (Sandbox Code Playgroud)
我用来执行查找.然而,这表现得相当糟糕:
(time (doseq [x (range 500)]
(my-map [1 2 8])))
"Elapsed time: 170 msecs"
Run Code Online (Sandbox Code Playgroud)
在同一台机器上,Clojure可以在大约236毫秒内完成500,000,或者大约700倍.虽然Clojure比ClojureScript更快并不出人意料,但我很困惑为什么ClojureScript会慢得多.
关于如何在ClojureScript中以高效且可读的方式制作简单的多值查找地图的任何想法?我知道做一堆ifs而不是使用矢量键解决方案肯定会更快,但我正在寻找一些更具可读性/可维护性的东西.
只是为了更新更多信息.以上是在Firefox中完成的,因此比V8慢.下列:
(def my-map2
(into cljs.core.PersistentHashMap/EMPTY
{[1 2 3] 1
[1 2 4] 5
[3 4 2] 3
[4 5 3] 3
[5 2 5] 6
[9 2 1] 5
[8 3 1] 6}))
(defn p1 []
(let [v [1 2 8]]
(dotimes [_ 5]
(time (dotimes [_ 500000]
(get my-map2 v))))))
Run Code Online (Sandbox Code Playgroud)
得到:
"Elapsed time: 3295 msecs"
"Elapsed time: 3246 msecs"
"Elapsed time: 3113 msecs"
"Elapsed time: 3107 msecs"
"Elapsed time: 3121 msecs"
Run Code Online (Sandbox Code Playgroud)
在Chromium版本25.0.1364.160 Ubuntu 13.04(25.0.1364.160-0ubuntu3).所以在ClojureScript中,Clojure的速度仍然比Clojure快13倍,但这比之前要好得多.另请注意,我是在浏览器repl中直接运行它.
在我的机器上运行你的高级编译的确切示例需要大约14毫秒的1.7ghz Macbook Air运行一个相对较新的源自源码的v8.
为了确保我们对我们认为我们正在进行基准测试的基准测试,最好写下这样的事情:
(let [v [1 2 8]]
(dotimes [_ 5]
(time
(dotimes [_ 500000]
(get my-map v)))))
Run Code Online (Sandbox Code Playgroud)
在我的机器上,Clojure JVM在机器上需要大约70ms.ClojureScript在大约3600ms左右运行,因此大约慢50倍.为什么?这是因为我们默认使用PersistentArrayMap,在使用复杂键定义小哈希映射时Clojure不会这样做.
如果我们这样定义my-map会发生什么:
(def my-map
(into cljs.core.PersistentHashMap/Empty
[[1 2 3] 1
[1 2 4] 5
[3 4 2] 3
[4 5 3] 3
[5 2 5] 6
[9 2 1] 5
[8 3 1] 6]))
Run Code Online (Sandbox Code Playgroud)
然后基准测试需要大约170毫秒,这与Clojure JVM相差无几.
所以Clojure实现了很多优化,我们尚未实现这些优化.我仍然会说,对于惯用的Clojure代码,我认为在V8等高度优化的JavaScript引擎上,我们所希望的最好是Clojure JVM的2-10倍.
| 归档时间: |
|
| 查看次数: |
453 次 |
| 最近记录: |