Loop and recur


Many functional programming models prefer to express repetition by recursive function calls.

In Phel's iteration process, there is a highly functional and convenient for macro, but there is also a loop special form that performs more primitive loop processing.

Loop Document | Control flow | The Phel Language

Phel's loop allows you to write repetitive processing just like a recursive function.

(loop [sum 0
       cnt 10]
  (if (= cnt 0)
    (recur (+ cnt sum) (dec cnt))))
=> 55

When the same function is written as a recursive function, it looks like this:

(defn my-sum-to-n [sum cnt]
  (if (= cnt 0)
    (my-sum-to-n (+ cnt sum) (dec cnt))))
(my-sum-to-n 0 10)
=> 55

There are some differences between the loop format and the recursive function format. When calling as recursion, the loop format specifies recur, but the recursive function format specifies its own function name my-sum-to-n. For everything else, you can see that you can use loop to write iterations in the same way you would write recursive functions.

However, there is one more thing to keep in mind. The recursive structure of loop must be tail recursive. This means that recur can only be placed at the location where it is evaluated last in the iteration process within loop. If you try to place recur in any other location, the following error will be displayed:

ERROR: Can't call 'recur here

If this error is displayed, please check whether the recursive structure of loop is tail recursive.

Note: Tail recursion is a recursive function where the recursive call is the final action in the function. This means the function has nothing else to do after the recursive call, which makes it possible for the compiler or interpreter to optimize the function by transforming it into a loop.