# Pattern Matching

Adds native pattern matching to Scheme. Supports pattern-oriented dispatch of function arguments (`pdefine`

), pattern bindings in `let`

-like statements (`plet`

) and pattern switch statements (`pcase`

). The pattern language was inspired by the 6.945 Pattern Matcher, although no code was borrowed.

Pattern language reference is available here.

### Macros

**plet** *({(pattern datum)}) body*

Matches patterns against datums, and executes `body`

in an environment with pattern variables bound. For example, here's how one might use `plet`

to implement vector addition, where a vector is a cons pair:

(define vec1 (cons 1 2))
;Value: vec1
(define vec2 (cons 3 4))
;Value: vec2
(define (vector-add x y)
(plet (((?x1 . ?x2) x)
((?y1 . ?y2) y))
(cons (+ x1 y1) (+ x2 y2))))
;Value: vector-add
(vector-add vec1 vec2)
;Value 86: (4 . 6)

**plet*** *({(pattern datum)}) body*

Like `plet`

, but each subsequent pattern-datum pair is evaluated in an environment with all previous matches bound.

(plet* ((p1 d1)
(p2 d2)
...
(pn dn))
e1
e2
...)

is equivalent to

(plet ((p1 d1))
(plet ((p2 d2))
...
(plet ((pn dn)
e1
e2
...)))).

**pdefine** *(name {argument pattern}) body*

Defines a procedure that dispatches based on argument patterns. For example, `pdefine`

might be used to define the factorial function:

(pdefine (fact 0) 1)
;Value: ok
(pdefine (fact ?n) (* n (fact (-1+ n))))
;Value: ok
(fact 5)
;Value: 120

Similarly, one might use

`pdefine`

to implement vector addition:

(pdefine (vector-add (?x1 . ?x2) (?y1 . ?y2))
(cons (+ x1 y1) (+ x2 y2)))
;Value: ok
(vector-add (cons 1 2) (cons 3 4))
;Value 89: (4 . 6)

Argument patterns can utilize all features of the pattern language, such as variable-length segments. In the example below. Anonymous segment patterns are used to check whether a list contains at least one number:

(pdefine (has-number? (??prefix (? num ,number?) ??suffix)) #t)
;Value: ok
(pdefine (has-number? ?obj) #f)
;Value: ok
(has-number? '(a b c 1 d e))
;Value: #t
(has-number? '(a b c d e))
;Value: #f

**Note**: Functions created using

`pdefine`

are bound in

`user-initial-environment`

.

**pcase** *datum {(pattern {expression})}*

Looks for the first `pattern`

that matches `datum`

, and executes the associated `expression`

s in an environment with bound pattern variables, returning then result. If no patterns match. the return value is undefined.

Example:

(pdefine (find ?elt ?a-list)
(pcase a-list
((??prefix ,elt ??suffix) elt)
(? #f)))
;Value: ok
(find 1 '(2 3 4 5))
;Value: #f
(find 1 '(2 3 a b 1 7 8))
;Value: 1
(find 'b '(2 3 a b 1 7 8))
;Value: b

Scheme Power Tools Documentation

(c) Maciej Pacula 2010-2011

http://mpacula.com