Reputation: 495
I know this example is trivial because I think there is a clojure library function that will do this, that is not the point.
I have the following code
(defn makelistres [a b res]
(if (= a b) res (makelistres a (dec b) (conj res b))))
(defn makelist [a b]
(makelistres a b [])
)
Is there a way to do the same effect without having to pass the list as a parameter? Such as throwing it on the stack
Such as
(defn test [a b]
(if (= a b) 0 (+ 1 (test a (dec b))))
)
Don't know if the parenthesis match up, as I wrote this in this text box, but you get the point.
Upvotes: 0
Views: 87
Reputation: 8088
John
There are a couple of ways:
(def res [1,2,3,4,5])
However this requires a priori definition of the data before calling makelistres
. There are ways to do this.
(def res-val (atom [])
This is more flexible using atom based functions to set and retrieve programmatically. However; you are using a mutable (stateful) object. Your ideology may shun this!
Because you are changing the content of res
the atom
approach seems more suited. You would basically set the value of the res (using swap)
item from makelist
and derefing (e.g. @res)
it or modifying it in the recursion of makelistres
.
Upvotes: -2
Reputation: 17859
is it an option to add one more arity to a function, which will then call the function with additional arg (empty vector) ?
like this:
(defn makelist
([a b] (makelist a b []))
([a b res]
(if (== a b) res (makelist a (dec b) (conj res b)))))
in repl:
user> (makelist 1 10)
[10 9 8 7 6 5 4 3 2]
if not, the loop
will do:
(defn makelist [a b]
(loop [a a b b res []]
(if (== a b)
res
(recur a (dec b) (conj res b)))))
or like this (since a
is not changed):
(defn makelist [a b]
(loop [b b res []]
(if (== a b)
res
(recur (dec b) (conj res b)))))
but yeah, there is a lib function for that:
(range 10 1 -1)
Upvotes: 4