What is the idiomatic way to prepend to a vector in Clojure?

0x89 picture 0x89 · Nov 4, 2010 · Viewed 26.6k times · Source

Prepending to a list is easy:

user=> (conj '(:bar :baz) :foo)
(:foo :bar :baz)

Appending to a vector is easy:

user=> (conj [:bar :baz] :foo) 
[:bar :baz :foo]

How do I (idiomatically) prepend to a vector, while getting back a vector? This does not work as it returns a seq, not a vector:

user=> (cons :foo [:bar :baz])     
(:foo :bar :baz)

This is ugly (IMVHO):

user=> (apply vector (cons :foo [:bar :baz])) 
[:foo :bar :baz]

Note: I basically just want a datastructure that I can append and prepend to. Appending to large lists should have a large performance penalty, so I thought of vectors..

Answer

kotarak picture kotarak · Nov 4, 2010

Vectors are not designed for prepending. You have only O(n) prepend:

user=> (into [:foo] [:bar :baz])
[:foo :bar :baz]

What you want is most likely a finger tree.