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

4. Generic Procedures

Like an ordinary Scheme procedure, a generic procedure takes arguments, performs a series of operations, and perhaps returns useful values. An ordinary procedure has a single body of code that is always executed when the procedure is called. A generic procedure has a set of multiple bodies of code, called methods, from which a subset is selected for execution. The selected bodies of code and the manner of their combination are determined by the classes of one or more of the arguments to the generic procedure.

Ordinary procedures and generic procedures are called with identical procedure-call syntax.

Generic procedures are true procedures that can be passed as arguments, returned as values, and otherwise used in all the ways an ordinary procedure may be used. In particular, generic procedures satisfy the predicate procedure?.

4.1 Generic Procedure Datatype  
4.2 Method Storage  
4.3 Effective Method Procedure  


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

4.1 Generic Procedure Datatype

The following definitions are used to construct and inspect generic procedures.

Procedure: make-generic-procedure arity [name]
Creates and returns a new generic procedure. The generic procedure requires arity arguments.

Arity may take one of the following forms. An exact positive integer specifies that the procedure will accept exactly that number of arguments. A pair of two exact positive integers specifies inclusive lower and upper bounds, respectively, on the number of arguments accepted; the CDR may be #f indicating no upper bound.

Name is used for debugging: it is a symbol that has no role in the semantics of the generic procedure. Name may be #f to indicate that the generic procedure is anonymous. If name is not specified, it defaults to #f.

Examples:

 
(define foo-bar (make-generic-procedure 2))

(define foo-baz (make-generic-procedure '(1 . 2) 'foo-baz))

(define foo-mum (make-generic-procedure '(1 . #f)))

Syntax: define-generic name lambda-list
Defines name to be a generic procedure. Lambda-list is an ordinary parameter list, which is exactly like the parameter list in a lambda special form. This expands into

 
(define name
  (make-generic-procedure arity
                          (quote name)))

where arity is determined from lambda-list.

Examples (compare to examples of make-generic-procedure):

 
(define-generic foo-bar (x y))

(define-generic foo-baz (x #!optional y))

(define-generic foo-mum (x . y))

Procedure: generic-procedure? object
Returns #t if object is a generic procedure, otherwise returns #f. Note that every generic procedure satisfies the predicate procedure?.

Procedure: generic-procedure-arity generic-procedure
Returns the arity of generic-procedure, as specified in the call to make-generic-procedure. The returned arity must not be modified.

Procedure: generic-procedure-name generic-procedure
Returns the name of generic-procedure, as specified in the call to make-generic-procedure.


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

4.2 Method Storage

Methods are stored in generic procedures. When a generic procedure is called, it selects a subset of its stored methods (using method-applicable?), and arranges to invoke one or more of the methods as necessary. The following definitions provide the means for adding methods to and removing them from a generic procedure.

Procedure: add-method generic-procedure method
Adds method to generic-procedure. If generic-procedure already has a method with the same specializers as method, then the old method is discarded and method is used in its place.

Procedure: delete-method generic-procedure method
Removes method from generic-procedure. Does nothing if generic-procedure does not contain method.

Procedure: add-methods generic-procedure methods
Adds methods, which must be a list of methods, to generic-procedure. Equivalent to calling add-method on each method in methods.

Procedure: generic-procedure-methods generic-procedure
Returns a list of the methods contained in generic-procedure. The returned list must not be modified.


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

4.3 Effective Method Procedure

When a generic procedure is called, it arranges to invoke a subset of its methods. This is done by combining the selected methods into an effective method procedure, or EMP, then tail-recursively invoking the EMP. compute-effective-method-procedure is the procedure that is called to select the applicable methods and combine them into an EMP.

Procedure: compute-effective-method-procedure generic-procedure classes
Collects the applicable methods of generic-procedure by calling method-applicable? on each method and on classes. Combines the resulting methods together into an effective method procedure, and returns that EMP.

Procedure: compute-method generic-procedure classes
This procedure is like compute-effective-method-procedure, except that it returns the result as a method whose specializers are classes.

compute-method is equivalent to

 
(make-method classes
             (compute-effective-method-procedure generic-procedure
                                                 classes))


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

This document was generated by Chris Hanson on July, 18 2001 using texi2html