Common Lisp: Why progn is a special form?
Asked Answered
T

2

17

Since Common Lisp's function arguments evaluate in left-to-right order, why wouldn't use an ordinary function:

(defun progn2 (&rest body)
  (first (last body)))

instead of special form?

Taste answered 16/6, 2013 at 20:46 Comment(2)
Doesn't defun already include an implicit progn ? Check the macro expansion of defun.Canula
Both @sds's and @RainerJoswig's answers make important points. The values in @sds's answer is something that you might catch once in a while, and the behavior that @RainerJoswig describes is very important, especially once you start putting macro-based top-level forms in your source; if these produce more than form that should be treated as top-level, then you need progn.Idden
C
27

There is also another feature of PROGN which you can't get with a function:

Imagine this code in a file of Common Lisp code:

(progn
  (defmacro foo () ))

vs.

(my-progn
  (defmacro foo () ))

With using PROGN the compiler will treat the DEFMACRO form as a top-level form. That means for example that the compiler notes that there is a macro definition and makes it available in the compile-time environment.

Using a function MY-PROGN, the compiler won't recognize the DEFMACRO form, because it is not at top-level.

Colubrid answered 17/6, 2013 at 7:36 Comment(1)
What top-level-form means?Missus
T
24

progn returns all the values of the last form it evaluates, your function returns just the first one:

(progn (values 1 2 3)) 
=>  1, 2, 3
(progn2 (values 1 2 3)) 
=>  1

Another critical feature of progn (mentioned by Rainer first) is that it keeps all its forms top-level, which makes it possible for macros to expand to multiple forms (see, e.g., my answer to "“value returned is unused” warning when byte-compiling a macro").

Tetragon answered 16/6, 2013 at 22:3 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.