Subject: `match' bug ?

From: Andy Wingo <[email-masked]>
Date: Sat, 24 Sep 2011 17:01:37 +0200

Hi Alex,

We are getting the following bug in Guile:

    > (use-modules (ice-9 match))

This imports your `match' library.

    > (define a '(1))
    > (match a (((and a 1)) a) (_ #f))
    1

Here we destructured the first element from '(1).

    > (define a '(1 2))
    > (match a ((and (a 2) (1 b)) (+ a b)) (_ #f))
    #f

Now we are trying to destructure the first two elements from '(1 2).
But it doesn't work!  OTOH it does work if we rename the pattern vars:

    > (match a ((and (x 2) (1 y)) (+ x y)) (_ #f))
    3

Can you reproduce this bug on other Schemes?  Could it be that the code
to extract vars to be bound is erroneously propagating the var bound to
the input value?  Or is it a bug in Guile?

Stefan Israelsson Tampe reports that the following redefinition of
`match' fixes the problem for him:

  (define-syntax match
    (syntax-rules ()
      ((match)
       (match-syntax-error "missing match expression"))
      ((match atom)
       (match-syntax-error "no match clauses"))
      ((match (app ...) (pat . body) ...)
       (let ((v (app ...)))
         (match-next v ((app ...) (set! (app ...))) (pat . body) ...)))
      ((match #(vec ...) (pat . body) ...)
       (let ((v #(vec ...)))
         (match-next v (v (set! v)) (pat . body) ...)))
      ((match atom (pat . body) ...)
       (let ((v atom))
         (match-next v (atom (set! atom)) (pat . body) ...)))))

As you see the last case introduces a `let'.

Regards,

Andy
-- 
http://wingolog.org/