diff options
Diffstat (limited to '')
-rw-r--r-- | monad/state.scm | 33 |
1 files changed, 19 insertions, 14 deletions
diff --git a/monad/state.scm b/monad/state.scm index 471e756..40c9ff5 100644 --- a/monad/state.scm +++ b/monad/state.scm @@ -1,13 +1,26 @@ +;;; Commentary: +;; +;; The state monad! +;; State is best modelled monadically as a function taking a state object, and +;; returning another state object. This state object is in turn represented as i +;; list where the first value is the last value returned, and the secound value +;; is the internal state. +;; +;; All access to this internal value is done through the methods @code{get}, +;; @code{put}, and @code{modify}. +;; +;; One side effect of the @code{<state>} object not being directly accessible is +;; that my trick for multiple dispatch return doesn't work. Which is why this +;; modules also exports @code{return-state} directly. +;; +;;; Code: + (define-module (monad state) #:use-module (oop goops) #:use-module (ice-9 match) #:use-module (monad) #:export (return-state run-state get put modify) - #:re-export (>>= >> fmap return)) - - -;; Alternative implementation of get. -;; See https://hackage.haskell.org/package/mtl-2.2.1/docs/src/Control.Monad.State.Class.html#get + #:re-export (>>= >> return)) ;;; newtype State = st-list -> st-list @@ -48,10 +61,6 @@ ((v _) ((proc (f v)) new-st-list))))) -;; (define-stateful-method ((>> (a <state>) (b <state>)) st-list-a) -;; (let ((st-list-b ((proc a) st-list-a))) -;; ((proc b) st-list-b))) - (define-stateful ((return-state v) st-list) "Sets the return value to v" (cons v (cdr st-list))) @@ -69,15 +78,11 @@ (list '() v)) (define-stateful ((modify proc) st-list) + "Applies proc to the value stored in state, and stores it back" (match st-list ((r s) (list '() (proc s))))) -;; (define-stateful-method ((fmap (f <procedure>) (s <state>)) st-list) -;; (match ((proc s) st-list) -;; ((r st) -;; (list (f r) st)))) - (define-method (run-state (st <state>) init) "Exec state with init as starting state value and st." ((proc st) (list init init))) |