functioncommon-lispoptional-parameterskeyword-argumentparameter-list

When is it appropriate to use keyword parameters vs optional?


Besides the cosmetic differences, what is the difference between key and optional these:


(defun play (&key now)
   ...)


(defun play (&optional now)
   ...)

As i understand it, in both cases:

  1. they are optional
  2. neither returns a list to the function like &rest

Solution

  • &optional

    Optional arguments are, hmm, optional. You can omit them and they may have default values. They need to be provided in order.

    (defun hello-world (&optional (message "Hi there!")
                                  (stream *standard-output*))
      (format stream "Hello World: ~a" message)
      (finish-output stream))
    
    (hello-world "Good morning!")
    

    Above omits the output stream, since it is optional and has a default value.

    (with-output-to-string (stream)
      (hello-world "Good morning!" stream))
    

    Above provides a stream, since we don't want to use the default value.

    Thus the following three call variations are possible:

    (hello-world "Good morning!" stream)
    (hello-world "Good morning!")
    (hello-world)
    

    &key

    Keyword arguments are named, optional and can be provided in any order:

    (defun hello-world (&key (message "Hi there!")
                             (stream *standard-output*))
      (format stream "Hello World: ~a" message)
      (finish-output stream))
    

    Now all the following five call variations are possible:

    (hello-world :message "Good morning!" :stream stream)
    (hello-world :stream  stream :message "Good morning!")
    (hello-world :message "Good morning!")
    (hello-world :stream stream)
    (hello-world)
    

    One can provide the keyword/value pairs in any order, omit some or omit all.

    Benefits of keyword arguments

    Thus keyword arguments give a lot of flexibility:

    The price to pay: keyword arguments may make some calls slower than calls with fixed parameter lists.

    When to use keyword parameters?

    Developers will write functions, macros, ... with keyword parameters when there are multiple (even many) optional arguments without clear order preference. The more readable code is an added advantages.