Skip to content

Instantly share code, notes, and snippets.

@jaredly
Last active January 28, 2021 03:32
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jaredly/7ab23c143f8da81febd5c9f7421531ca to your computer and use it in GitHub Desktop.
Save jaredly/7ab23c143f8da81febd5c9f7421531ca to your computer and use it in GitHub Desktop.
This is able to at least handle the "jump between two handlers" aspect of abilities. will see how well I make it through the rest of the test cases. This is run using chicken scheme.
(define stack '())
(define (throw-effect k effect)
(let* ((handler (car stack)) (name (car handler)) (fn (cadr handler)))
(set! stack (cdr stack))
(print "Calling " name)
(fn (cons 'effect (cons k effect)))
)
)
(define (throw-pure value)
(let* ((handler (car stack)) (name (car handler)) (fn (cadr handler)))
(set! stack (cdr stack))
(print "Calling " name)
(fn (list 'pure value))
)
)
(define (rethrow eff)
(let ((k (cadr eff))
(ef (cddr eff)))
(throw-effect k eff)))
(define (add-handler name handler)
(print "add handler " name " " handler " " stack)
(set! stack (cons (list name handler) stack))
(print "now " stack)
)
(define (getInt)
(call/cc (lambda (k) (throw-effect k (list 'getInt)))))
(define (handle name inner handler)
(handler (call/cc (lambda (k)
(print "adding handler " name)
(add-handler name k) ; TODO we'll have to pop at some point?
(let ((value (inner)))
(print "Got value " name " " value)
(throw-pure value)
; (list 'pure value)
)
)))
)
(print)
(define f_01
(handle "top"
(lambda () (getInt))
(lambda (eff)
(print "top" eff)
(match eff
[('pure a) (list a 2)]
[('effect k 'getInt)
(handle "inner"
(lambda () (k 5))
(lambda (eff)
(print "inner" eff)
(match eff
[('pure a) (list a 3)]
[_ (rethrow eff)]
)
)
)
]
[_ (rethrow eff)]
)
)
)
)
(print f_01)
ability abilities.a_01 where
getInt : Int
abilities.f_01 = handle (abilities.a_01.getInt) with cases
{ a } -> (a, 2)
{ abilities.a_01.getInt -> k } ->
handle (k +5) with cases
{ a } -> (a, 3)
abilities.t_01 = abilities.f_01 == (+5, 3)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment