mirror of
https://github.com/metosin/reitit.git
synced 2025-12-18 17:01:11 +00:00
Much faster without transients
This commit is contained in:
parent
81b9bdceef
commit
659aac7fd0
4 changed files with 12 additions and 17 deletions
|
|
@ -3,7 +3,6 @@ package reitit;
|
|||
// https://www.codeproject.com/Tips/1190293/Iteration-Over-Java-Collections-with-High-Performa
|
||||
|
||||
import clojure.lang.IPersistentMap;
|
||||
import clojure.lang.ITransientMap;
|
||||
import clojure.lang.Keyword;
|
||||
import clojure.lang.PersistentArrayMap;
|
||||
|
||||
|
|
@ -35,26 +34,20 @@ public class Trie {
|
|||
case '+':
|
||||
hasPlus = true;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
return decode(chars, begin, end, hasPercent, hasPlus);
|
||||
}
|
||||
|
||||
public static class Match {
|
||||
final ITransientMap params = PersistentArrayMap.EMPTY.asTransient();
|
||||
public IPersistentMap params = PersistentArrayMap.EMPTY;
|
||||
public Object data;
|
||||
|
||||
public IPersistentMap parameters() {
|
||||
return params.persistent();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
Map<Object, Object> m = new HashMap<>();
|
||||
m.put(Keyword.intern("data"), data);
|
||||
m.put(Keyword.intern("params"), parameters());
|
||||
m.put(Keyword.intern("params"), params);
|
||||
return m.toString();
|
||||
}
|
||||
}
|
||||
|
|
@ -165,8 +158,6 @@ public class Trie {
|
|||
@Override
|
||||
public Match match(int i, int max, char[] path, Match match) {
|
||||
if (i < max && path[i] != end) {
|
||||
boolean hasPercent = false;
|
||||
boolean hasPlus = false;
|
||||
int stop = max;
|
||||
for (int j = i; j < max; j++) {
|
||||
final char c = path[j];
|
||||
|
|
@ -174,12 +165,10 @@ public class Trie {
|
|||
stop = j;
|
||||
break;
|
||||
}
|
||||
hasPercent = hasPercent || c == '%';
|
||||
hasPlus = hasPlus || c == '+';
|
||||
}
|
||||
final Match m = child.match(stop, max, path, match);
|
||||
if (m != null) {
|
||||
m.params.assoc(key, decode(path, i, stop, hasPercent, hasPlus));
|
||||
m.params = m.params.assoc(key, decode(path, i, stop));
|
||||
}
|
||||
return m;
|
||||
}
|
||||
|
|
@ -218,7 +207,7 @@ public class Trie {
|
|||
@Override
|
||||
public Match match(int i, int max, char[] path, Match match) {
|
||||
if (i < max) {
|
||||
match.params.assoc(parameter, decode(path, i, max));
|
||||
match.params = match.params.assoc(parameter, decode(path, i, max));
|
||||
match.data = data;
|
||||
return match;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -226,7 +226,7 @@
|
|||
|
||||
(defn lookup [matcher path]
|
||||
#?(:clj (if-let [match ^Trie$Match (Trie/lookup ^Trie$Matcher matcher ^String path)]
|
||||
(->Match (.data match) (.parameters match)))
|
||||
(->Match (.data match) (.params match)))
|
||||
:cljs (if-let [match (match matcher 0 (count path) path)]
|
||||
(let [params (if-let [path-params (:path-params match)]
|
||||
(persistent! path-params)
|
||||
|
|
|
|||
|
|
@ -348,6 +348,7 @@
|
|||
;; 64µs (trie-router, no injects, optimized) - 124µs (clojure)
|
||||
;; 63µs (trie-router, no injects, switch-case) - 124µs (clojure)
|
||||
;; 63ns (trie-router, no injects, direct-data)
|
||||
;; 54ns (trie-router, non-transient params)
|
||||
(let [requests (mapv route->req routes)]
|
||||
(title "all")
|
||||
(cc/quick-bench
|
||||
|
|
|
|||
|
|
@ -572,6 +572,7 @@
|
|||
;; 326ns (java-segment-router)
|
||||
;; 194ns (trie)
|
||||
;; 160ns (trie, prioritized)
|
||||
;; 130ns (trie, non-transient, direct-data)
|
||||
(b! "reitit" reitit-f)
|
||||
|
||||
;; 2845ns
|
||||
|
|
@ -585,16 +586,18 @@
|
|||
;; 373ns (trie)
|
||||
;; 323ns (trie, prioritized)
|
||||
;; 289ns (trie, prioritized, zero-copy)
|
||||
;; 266ns (trie, non-transient, direct-data)
|
||||
(b! "reitit-ring" reitit-ring-f)
|
||||
|
||||
;; 385ns (java-segment-router, no injects)
|
||||
;; 271ms (trie)
|
||||
;; 240ns (trie, prioritized)
|
||||
;; 214ns (trie, non-transient, direct-data)
|
||||
(b! "reitit-ring-fast" reitit-ring-fast-f)
|
||||
;; 240ns (trie, prioritized, zero-copy)
|
||||
|
||||
;; 2553ns (linear-router)
|
||||
;; 630ns (segment-router-backed)
|
||||
;; 464ns (trie, non-transient, direct-data)
|
||||
(b! "reitit-ring-linear" reitit-ring-linear-f)
|
||||
|
||||
;; 2137ns
|
||||
|
|
@ -627,6 +630,7 @@
|
|||
;; 629ms (arraylist)
|
||||
;; 409ns (transient)
|
||||
;; 409ns (staticMultiMatcher)
|
||||
;; 305ns (non-persistent-params)
|
||||
(let [app (ring/ring-handler (ring/router opensensors-routes) {:inject-match? false, :inject-router? false})
|
||||
request {:uri "/v1/users/1/devices/1", :request-method :get}]
|
||||
(doseq [[p r] (-> app (ring/get-router) (r/routes))]
|
||||
|
|
@ -638,6 +642,7 @@
|
|||
(prof/start {})
|
||||
; "Elapsed time: 9183.657012 msecs"
|
||||
; "Elapsed time: 8674.70132 msecs"
|
||||
; "Elapsed time: 6714.434915 msecs"
|
||||
(time
|
||||
(dotimes [_ 20000000]
|
||||
(app request)))
|
||||
|
|
|
|||
Loading…
Reference in a new issue