How to convert from kebab-case to camelCase in Clojure
Here are six functions that do that. Pick your favourite. It won't be the best performing one. Can you guess which that is? Scroll down for answer.
(defn kebab->camel1 [^String kebab]
(->> kebab
(reduce
(fn [[buf ucase] c]
(let [dash (= \- c)]
[(if dash
buf
(conj buf (if ucase
(Character/toUpperCase c)
c)))
dash]))
[[] false])
first
(apply str)))
(defn kebab->camel2 [^String kebab]
(->> (map
(fn [cur prev] (if (= \- prev)
(Character/toUpperCase cur)
cur)) kebab (cons nil kebab))
(filter #(not= \- %))
(apply str)))
(defn kebab->camel3 [^String kebab]
(loop [buf []
ucase false
rst kebab]
(if (seq rst)
(let [c (first rst)
dash (= \- c)]
(recur (if dash
buf
(conj buf (if ucase
(Character/toUpperCase c)
c)))
dash
(rest rst)))
(apply str buf))))
(defn kebab->camel4 [^String kebab]
(->> (map
(fn [[prev cur]] (if (= \- prev)
(Character/toUpperCase cur)
cur)) (partition 2 1 (cons nil kebab)))
(filter #(not= \- %))
(apply str)))
(defn kebab->camel5 [^String kebab]
(let [pv (volatile! nil)
sb (StringBuilder. (count kebab))]
(doseq [c kebab]
(let [prior @pv
dash (= \- c)]
(vreset! pv dash)
(when-not dash (.append
sb
(if prior
(Character/toUpperCase c) c)))))
(.toString sb)))
(defn kebab->camel6 [^String kebab]
(let [buf (.toCharArray kebab)
len (count buf)]
(loop [src 0 dst 0 ucase nil]
(if (< src len)
(let [c (aget buf src)
dash (= \- c)]
(when-not dash (aset buf dst (if ucase (Character/toUpperCase c) c)))
(recur (inc src) (if dash dst (inc dst)) dash))
(String. buf 0 dst)))))
To see which is best we do this
(let [kebab (->> (.ints (java.util.Random. 17) 0 31)
.iterator
iterator-seq
dedupe
(map #(nth "abcdefghijklmnopqrstuvwxyz-----" %))
(take 10000)
(apply str))
time-fn (fn [f]
(let [start (System/nanoTime)]
(f)
(/ (double (- (System/nanoTime) start)) 1000000.0)))]
(for [f [kebab->camel1
kebab->camel2
kebab->camel3
kebab->camel4
kebab->camel5
kebab->camel6]]
[f (time-fn #(dotimes [_ 1000] (f kebab)))]))
and get results like these
([#function[user/kebab->camel1] 9064.630932]
[#function[user/kebab->camel2] 11520.793361]
[#function[user/kebab->camel3] 8440.000948]
[#function[user/kebab->camel4] 20740.882337]
[#function[user/kebab->camel5] 8455.671506]
[#function[user/kebab->camel6] 99.724767])
No comments:
Post a Comment