As already answered, all arguments to a call to some function f are evaluated before the result of applying f is computed. Does it however mean that cond
, or if
, or both should be special forms?
Well, first, if you have if
, you can easily simulate a cond
with nested tests. Conversely, if
is just a degenerate form of cond
. So you can say that it is sufficient to have one of them a special form. Let's choose if
because it is simpler to specify.
So shall if
be special?
It doesn't really need to...
If the underlying question is "is if
expressible in terms of a smaller set of special forms?", then the answers is yes: just implement if
in terms of functions:
(define true-fn (lambda (then else) (then)))
(define false-fn (lambda (then else) (else)))
Whenever you can return a boolean, you return one of the above function instead.
You could for example decide to bind #t
and #f
to those functions.
Notice how they call one of the two input parameters.
((pair? x) ;; returns either true-fn or false-fn
(lambda () (+ x 1))
(lambda () x))
...but why code in lambda calculus?
Evaluating code conditionally is really a fundamental operation of computing. Trying to find a minimal special forms where you cannot express that directly leads to a poorer programming language from the perspective of the programmer, however "clean" the core language is.
From a certain point of view, the if
form (or cond
) is necessary because without them it becomes really hard to express conditional execution in a way that a compiler/interpreter can handle efficiently.
This document referenced by uselpa discuss using closures to implement if
, and concludes:
However, the syntactic inconvenience would be so great that even
Scheme defines if as a special form.
if
, but is correct forcond
as well: vepa.in/technology/why-is-if-a-special-form-in-scheme – Accoucheur