manpagez: man pages & more
info guile
Home | html | info | man
[ << ] [ < ] [ Up ] [ > ] [ >> ]         [Top] [Contents] [Index] [ ? ]

6.9.5 Case-lambda

R5RS’s rest arguments are indeed useful and very general, but they often aren’t the most appropriate or efficient means to get the job done. For example, lambda* is a much better solution to the optional argument problem than lambda with rest arguments.

Likewise, case-lambda works well for when you want one procedure to do double duty (or triple, or ...), without the penalty of consing a rest list.

For example:

(define (make-accum n)
  (case-lambda
    (() n)
    ((m) (set! n (+ n m)) n)))

(define a (make-accum 20))
(a) ⇒ 20
(a 10) ⇒ 30
(a) ⇒ 30

The value returned by a case-lambda form is a procedure which matches the number of actual arguments against the formals in the various clauses, in order. The first matching clause is selected, the corresponding values from the actual parameter list are bound to the variable names in the clauses and the body of the clause is evaluated. If no clause matches, an error is signalled.

The syntax of the case-lambda form is defined in the following EBNF grammar. Formals means a formal argument list just like with lambda (see section Lambda: Basic Procedure Creation).

<case-lambda>
   --> (case-lambda <case-lambda-clause>)
<case-lambda-clause>
   --> (<formals> <definition-or-command>*)
<formals>
   --> (<identifier>*)
     | (<identifier>* . <identifier>)
     | <identifier>

Rest lists can be useful with case-lambda:

(define plus
  (case-lambda
    (() 0)
    ((a) a)
    ((a b) (+ a b))
    ((a b . rest) (apply plus (+ a b) rest))))
(plus 1 2 3) ⇒ 6

Also, for completeness. Guile defines case-lambda* as well, which is like case-lambda, except with lambda* clauses. A case-lambda* clause matches if the arguments fill the required arguments, but are not too many for the optional and/or rest arguments.

Keyword arguments are possible with case-lambda*, but they do not contribute to the “matching” behavior. That is to say, case-lambda* matches only on required, optional, and rest arguments, and on the predicate; keyword arguments may be present but do not contribute to the “success” of a match. In fact a bad keyword argument list may cause an error to be raised.


[ << ] [ < ] [ Up ] [ > ] [ >> ]         [Top] [Contents] [Index] [ ? ]

This document was generated on February 3, 2012 using texi2html 5.0.

© manpagez.com 2000-2025
Individual documents may contain additional copyright information.