Skip to content

Instantly share code, notes, and snippets.

@kgadek
Created February 12, 2013 04:43
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 kgadek/4760294 to your computer and use it in GitHub Desktop.
Save kgadek/4760294 to your computer and use it in GitHub Desktop.
Monads somewhat explained w/ dense example. Read more: http://readlists.com/0bca8296 . Kudos to: bartoszmilewski.com .
import Control.Monad
data StackCalc a = StackCalc { runStackCalc :: [Int] -> ([Int], a) }
instance Monad StackCalc where
return x = StackCalc aux
where aux stack = (stack, x)
f >>= e = StackCalc aux
where aux stack = let (newstack, newval) = runStackCalc f stack
in runStackCalc (e newval) newstack
cPush :: Int -> StackCalc ()
cPush x = StackCalc aux
where aux stack = ((x:stack), ())
cPop :: StackCalc (Maybe Int)
cPop = StackCalc aux
where aux (s:stack) = (stack, Just s)
aux stack = (stack, Nothing)
cPeek :: StackCalc (Maybe Int)
cPeek = StackCalc aux
where aux ss@(s:stack) = (ss, Just s)
aux stack = (stack, Nothing)
cAdd :: StackCalc ()
cAdd = StackCalc aux
where aux (x:y:stack) = ((xy:stack), ())
where xy = x+y
aux stack = (stack, ())
cFibNext :: StackCalc Int
cFibNext = StackCalc aux
where aux (x:y:stack) = (xy:x:stack, xy)
where xy = x+y
aux stack = (stack, 0)
test = do
cPush 0
cPush 1
cFibNext
cFibNext
cFibNext
cFibNext
cFibNext
cFibNext
cFibNext
cFibNext
cPeek
cPeek
cPeek
cPeek
cPeek
cPeek
cPop
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment