Hi amb

A colleague introduced me to the amb operator. The best reference is Teach Yourself Scheme in Fixnum days.

(define-macro amb
  (lambda alts...
    `(let ((+prev-amb-fail amb-fail))
       (call/cc
        (lambda (+sk)

          ,@(map (lambda (alt)
                   `(call/cc
                     (lambda (+fk)
                       (set! amb-fail
                         (lambda ()
                           (set! amb-fail +prev-amb-fail)
                           (+fk 'fail)))
                       (+sk ,alt))))
alts...)

          (+prev-amb-fail))))))

In BASIC,
(amb 10 20 30)
roughly translates to


100 REM ------- AMB 1 2 3 -----------
102 PREV_FAIL = SAVE_PREV_GOTO
105 ON ERROR GOTO 115
110 RETURN 10
115 ON ERROR GOTO 125
120 RETURN 20
125 ON ERROR GOTO 13
130 RETURN 30
135 ON ERROR GOTO PREV_FAIL
140 RAISE ERROR
200 REM ------ AMB ----------------
210 RAISE ERROR

Leave a Reply