1. functions
    1. functions and parameters
    2. function data & lambda
  2. Floating Topic
  3. three basic components
    1. functions
    2. variables
      1. 3/4 names are functions
      2. object system is built upon a extension to functions
    3. macros
      1. macros are also functions, that are used to generate code
  4. defun
    1. (defun name (parameter*) "Optional documentation string." body-form*)
      1. (documentation 'fun-name 'function)
      2. parameter list
        1. required parameters
        2. optional parameters
        3. rest parameters
          1. a variable number of arguments
        4. key word parameters
        5. mixing different parameter types
          1. first the names of the required parameters
          2. second the optional parameters
          3. then the rest parameter
          4. finally the keyword parameter
    2. (defun hello ())
    3. (defun hello () () )
  5. optional parameters
    1. (defun foo (a b &optional c d) (list a b c d) )
      1. (foo 1 2) ==> (1 2 NIL NIL)
      2. (foo 1 2 3) ==> (1 2 3 NIL)
      3. (foo 1 2 3 4) ==> (1 2 3 4)
    2. (defun foo (a &optional (b 10)) (list a b))
      1. (foo 1 2) ==> (1 2)
      2. (foo 1) ==> (1 10)
    3. (defun foo (a b &optional (c 3 c-supplied-p)) (list a b c c-supplied-p))
      1. (foo 1 2) ==> (1 2 3 NIL)
      2. (foo 1 2 3) ==> (1 2 3 T)
      3. (foo 1 2 4) ==> (1 2 4 T)
  6. rest parameters
    1. (defun hello(&rest all) (print all) )
      1. (hello 1) => (1)
      2. (hello 1 2) => (1 2)
    2. (defun format (stream string &rest values) ...)
    3. (defun + (&rest numbers) ...)
  7. Keyword Parameters
    1. (defun foo (&key a b c) (list a b c))
      1. (foo) ==> (NIL NIL NIL)
      2. (foo :a 1) ==> (1 NIL NIL)
      3. (foo :b 1) ==> (NIL 1 NIL)
      4. (foo :c 1) ==> (NIL NIL 1)
      5. (foo :a 1 :c 3) ==> (1 NIL 3)
      6. (foo :a 1 :b 2 :c 3) ==> (1 2 3)
      7. (foo :a 1 :c 3 :b 2) ==> (1 2 3)
    2. (defun foo (&key (a 0) (b 0 b-supplied-p) (c (+ a b))) (list a b c b-supplied-p))
      1. (foo :a 1) ==> (1 0 1 NIL)
      2. (foo :b 1) ==> (0 1 1 T)
      3. (foo :b 1 :c 4) ==> (0 1 4 T)
      4. (foo :a 2 :b 1 :c 4) ==> (2 1 4 T)
  8. Mixing Different Parameter Types
    1. sequence. see /* section defun */
    2. valid combinations
      1. required parameters with one other flavor
      2. &optional and &rest parameters
    3. invalid combinations
      1. &optional with &key (defun foo (x &optional y &key z) (list x y z))
        1. (foo 1 2 :z 3) ==> (1 2 3)
        2. (foo 1) ==> (1 nil nil)
        3. (foo 1 :z 3) ==> ERROR
      2. &rest with &key (defun foo (&rest rest &key a b c) (list rest a b c))
        1. (foo :a 1 :b 2 :c 3) ==> ((:A 1 :B 2 :C 3) 1 2 3)
  9. Function Return Values. RETURN-FROM
    1. Function default returned value, The value of the last expression evaluated
    2. Special operation return-from
      1. return-from is used to return from a block of code defined with the BLOCK special operator
      2. TURN-FROM is a special operator whose first "argument" is the name of the block from which to return. This name isn't evaluated and thus isn't quoted.
      3. defun automatically wraps the whole function body in a block with the same name as the function
      4. evaluating a RETURN-FROM with the name of the function and the value you want to return will cause the function to immediately exit with that value.
      5. having to specify the name of the function you're returning from is a bit of a pain
    3. (defun foo (n) (dotimes (i 10) (dotimes (j 10) (when (> (* i j) n) (return-from foo (list i j))))))
  10. Functions As Data
    1. (defun foo (x) (* 2 x))
      1. CL-USER> (function foo) #<Interpreted Function FOO>
      2. CL-USER> #'foo #<Interpreted Function FOO>
      3. The syntax #' is syntactic sugar for FUNCTION
      4. just the way ' is syntactic sugar for QUOTE
    2. funcall
      1. (foo 1 2 3) === (funcall #'foo 1 2 3)
      2. (defun plot (fn min max step) (loop for i from min to max by step do (loop repeat (funcall fn i) do (format t "*")) (format t "~%")))
    3. apply
      1. (apply #'plot plot-data-list)
      2. also accept "loose" arguments as long as the last argument is a list
      3. (apply #'plot #'exp (pop plot-data-list))
  11. lambda
    1. (lambda (parameters) body)
      1. (funcall #'(lambda (x y) (+ x y)) 2 3) ==> 5
      2. ((lambda (x y) (+ x y)) 2 3) ==> 5
      3. (plot #'(lambda (x) (* 2 x)) 0 10 1)