Next: , Previous: , Up: Lists   [Contents][Index]


5.5.2.2 Building Lists

It has already been described how you can create lists using the Lisp reader; this method does have a drawback though: the list created is effectively static. If you modify the contents of the list and that list was created when a function was defined the list will remain modified for all future invocations of that function. This is not usually a good idea, consider the following function definition,

(defun bogus-function (x)
  "Return a list whose first element is nil and whose second element is X."
  (let
      ((result '(nil nil)))     ;Static list which is filled in each time
    (rplaca (cdr result) x)     ; the function is called
    result))

This function does in fact do what its documentation claims, but a problem arises when it is called more than once,

(setq x (bogus-function 'foo))
    ⇒ (nil foo)
(setq y (bogus-function 'bar))
    ⇒ (nil bar)               ;The first result has been destroyed
x
    ⇒ (nil bar)               ;See!

This example is totally contrived—no one would ever write a function like the one in the example but it does demonstrate the need for a dynamic method of creating lists.

Function: list #!rest elements

This function creates a list out of its arguments, if zero arguments are given the empty list, (), is returned.

(list 1 2 3)
    ⇒ (1 2 3)

(list (major-version-number) (minor-version-number))
    ⇒ (3 2)

(list)
    ⇒ ()
Function: list* arg1 arg2 … argn-1 argn

Creates a new list (arg1 arg2argn-1 . argn).

(list* 1 2 '(3 4))
    ⇒ (1 2 3 4)
Function: make-list length #!optional initial-value

This function creates a list length elements long. If the initial-value argument is given it defines the value of all elements in the list, if it is not defined they are all ().

(make-list 2)
    ⇒ (() ())

(make-list 3 t)
    ⇒ (t t t)

(make-list 0)
    ⇒ ()
Function: append #!rest lists

This function creates a new list with the elements of each of its arguments (which must be lists). Unlike the function nconc this function preserves the structure of all its arguments.

(append '(1 2 3) '(4 5))
    ⇒ (1 2 3 4 5)

(append)
    ⇒ ()

What actually happens is that all arguments but the last are copied, then the last argument is linked on to the end of the list (uncopied).

(setq foo '(1 2))
    ⇒ (1 2)
(setq bar '(3 4))
    ⇒ (3 4)
(setq baz (append foo bar))
    ⇒ (1 2 3 4)
(eq (nthcdr 2 baz) bar)
    ⇒ t

The following diagram shows the final state of the three variables more clearly,

foo--> +-----+-----+   +-----+-----+
       |  o  |  o----> |  o  |     |
       +--|--+-----+   +--|--+-----+
          |               |
          o--> 1          o--> 2   bar
          |               |          ->
baz--> +--|--+-----+   +--|--+-----+   +-----+-----+   +-----+-----+
       |  o  |  o----> |  o  |  o----> |  o  |  o----> |  o  |     |
       +-----+-----+   +-----+-----+   +--|--+-----+   +--|--+-----+
                                          |               |
                                           --> 3           --> 4

Note how foo and the first half of baz use the same objects for their elements—copying a list only copies its cons cells, its elements are reused. Also note how the variable bar actually references the mid-point of baz since the last list in an append call is not copied.

Function: remove elt list

Return a copy of list, with all elements the same as elt discarded (using the equal function to compare).

Function: remq elt list

Similar to the remove function, except that comparisons are made using eq.

Function: reverse list

This function returns a new list; it is made from the elements of the list list in reverse order. Note that this function does not alter its argument.

(reverse '(1 2 3 4))
    ⇒ (4 3 2 1)

As a postscript to this section, the function used as an example at the beginning could now be written as,

(defun not-so-bogus-function (x)
  (list nil x))

Also note that the cons function can be used to create lists by hand and to add new elements onto the front of a list. For example:

(setq x (list 1 2 3))
    ⇒ (1 2 3)
(setq x (cons 0 x))
    ⇒ (0 1 2 3)

Next: , Previous: , Up: Lists   [Contents][Index]