Return Styles: Pseud0ch, Terminal, Valhalla, NES, Geocities, Blue Moon. Entire thread

Haskell Nomads

Name: Anonymous 2008-09-23 13:47

So can anybody tell me in a way one can understand it what a fucking monad does?

Name: Anonymous 2008-09-25 15:01

We conjure the spirits of the computer with our voodoo spells.

Name: Anonymous 2008-09-25 18:25

>>40
There's nothing to it, really. Monads allow you to express a purely functional computation while keeping some aspect of that computation hidden or implicit. For example, if you wanted to write a function that returns a list of n random numbers using the function random :: (RandomGen g, Random a) => g -> (a, g), you'd write something like this:

nRandoms n gen
   | n <= 0 = ([], gen)
   | otherwise = (r:rs, gen'')
   where
      (r, gen') = random gen
      (rs, gen'') = nRandoms (n - 1) gen'


See how you have to explicitly handle the "state changes" of the random generator by passing it around? Well, if you turn the random function into a State monad:

randomS :: (RandomGen g, Random a) => State g a
randomS = State random


then you can write nRandoms like this:

nRandomsS n
   | n <= 0 = return []
   | otherwise = liftM2 (:) randomS (nRandomsS (n - 1))

nRandoms n gen = runState (nRandomsS n) gen


or even like this:

nRandoms n gen = runState (replicateM n randomS) gen


What this particular monad, the State monad, does is handle the state changes implicitly, so you don't have to worry about it. Here's (part of) the definition of that monad, see how simple it is:

newtype State s a = State { runState :: s -> (a, s) }

instance Monad (State s) where
    return a = State $ \s -> (a, s)
    m >>= k  = State $ \s -> let (a, s') = runState m s
                                 in runState (k a) s'


Hope this helps clear things up for you.

Name: Anonymous 2008-09-25 18:56

>>42
I'm more confused than ever. Thanks a lot

Name: Anonymous 2008-09-25 20:14

It is perfectly fine to write Haskell code without ever touching a monad (let's forget about the list and IO monads for now). However, as time progresses and experience accumulates, people inadvertently write Haskell code that fits the definition of the Haskell monad; they create and use their own monads and find the concept monads are simpler than first expected when someone points it out to them. This is what happened to me.

For me, monads are easy. I didn't study any math greater than high school level math. I failed to understand the tutorials on Haskell monads before I realised how powerful and elegant they are when a friend pointed out that I was writing and using my own monads. I found that some other people felt the same way about monads - the tutorials about monads are hard and confusing. This led me to conclude that monads are easy - explaining monads to the non-enlightened is not.

So I guess my point is to keep hacking in Haskell without bothering about monads. However, be aware that you're missing out on a very powerful tool.

Name: Anonymous 2008-09-25 20:49

>>42
this particular monad,
Nice effort, and the last bit almost makes sense, but you didn't really explain monads.  I'm tired of seeing discussions of a single instance, when as a whole they're apparently
1) not particularly related
2) wired into the compiler as special cases
3) able to segfault if used in any construct other than the ones handed down by ``SPJ'' Peyote-Joints himself.

Seriously, where does List get off being in the same category as IO?  Do the magicks attached to those have anything to do with being a monad?  What does it even mean for something to be a monad?

Name: Anonymous 2008-09-25 21:09

>>45
1) They aren't related.
2) If you're talking about the do notation, that's just syntactic sugar.
3) That didn't make sense.

A monad is just a data type that implements these functions:

(>>=) :: Monad m => m a -> (a -> m b) -> m b
(>>) :: Monad m => m a -> m b
return :: Monad m => a -> m a

If you're looking for it to mean more than that, you're either trolling, crazy, or trying to drive yourself crazy.

Name: Anonymous 2008-09-25 21:21

Oh yeah, and they also must obey these laws:

return a >>= f == f a
m >>= return == m
(m >>= f) >>= g == m >>= (\a -> f a >>= g)

Name: Anonymous 2008-09-25 21:21

>>45
If you think of the monad as a "computation strategy", you'll find that each different monad implements a different strategy. This explains why each monad is not really related.

You may find enlightenment in >>11.

Name: Anonymous 2008-09-25 23:07

>>46
2) I'm talking about how monads seem to be a gathering point for strange behaviors that (presumably) can't be implemented in the language itself, and whatever Haskell code may represent them is replaced by internal functions at compile time.
3) That's been my experience when a program I'm trying to write gets too tangled among the standard monads.  Even when GHC accepts the code, the runtime crashes on it.

If you're looking for it to mean more than that, you're either trolling, crazy, or trying to drive yourself crazy.
Or I've read basically anything ever written promoting/teaching Haskell, wherein so-called “monadic behavior” is touted as a major defining aspect of the language (rather than “hey I thought of a way to rearrange that function”) and the monads themselves are giant shadowy beasts of which we must never speak.

>>48
Thanks.

Name: Anonymous 2008-09-25 23:52

>>42
Thank you for your explanation, but i know that already. The reason why i still don't use haskell is that monads are said to do a lot more than they really do. Especially because they are called Monads and that they are used to encapsulate side effects. Call them wrappers, containers, templates, whatnot, but the name monads in itself has no apparent meaning and should go away.

And about how they encapsulate side effects (As far as i understand). Monads either force the compiler to execute a function with side effects exactly the number of times we want it and no known (or UNKNOWN) optimization can change the order or number of times or they are broken. But i could not find any article describing which laws of mathematics would enforce monads to act how people claim they do. And we talk about laws which can be enforced in a pure functional language using only the core concepts which weren't written to explicitly support monads, because the developers of haskell claim, that they didn't need to add special support for them.

If i think about it, we get several possible cases:
1. There are some rules which make monads possible in the most efficient manner without bad effects on the other parts of haskell in terms of run speed, stability and usability.
2. it is not possible to efficiently optimize haskell code, because the used laws are to strict, else they could not support monads and hence functions with side effects.
3. Monads are broken.
4. Haskell is not a pure functional language.

Name: Anonymous 2008-09-25 23:56

I'd jizzim all over Haskell's pretty little face.

Name: Anonymous 2008-09-25 23:57

>>50
forgot
5. Haskell is broken
6. Haskell has special support for Monads

the cases are all about side effects in haskell

Name: Anonymous 2008-09-26 0:39

and people still drink the Kool-Aid and claim that Haskell is a pure functional language.

Name: Anonymous 2008-09-26 1:12

>>50
Call them wrappers, containers, templates, whatnot, but the name monads in itself has no apparent meaning and should go away.
SPJ did not invent the term ``monad''. Your shitty vocabulary is no reflection on Haskell.

Name: Anonymous 2008-09-26 1:15

>>53
It is purely functional, but it is possible to write functions in C that aren't pure, but seem pure to the user.

In reality, no language can be absolutely purely functional, because then nothing would be happen. As SPJ has said in his slides, the goal is to merge the useful, dangerous languages which always allow side effects with the safe, useless ones which don't, so that we reach a sort of programming language nirvana.

Name: Anonymous 2008-09-26 1:20

>>50
Except it's not a function being executed N times and having side effects, it's a function being composed against itself to the Nth degree and having cumulative effects on a value invisibly threaded through the whole sequence.

Name: Anonymous 2008-09-26 2:07

>>54
right, some mathematican invented that shitty name and some other shitheads thought it was a good idea to rename old concepts (encapsulation) in programming with it, instead of using a name which describes what monads are good for. I wonder why some people try so hard to find creative names, which fit the topic.

>>56
>Except it's not a function being executed N times and having side effects, it's a function being composed against itself to the Nth degree and having cumulative effects on a value invisibly threaded through the whole sequence.
Which sounds good for me, as long as nobody wants to tell me now about how we put the world state into the monad or need to compute an actual value in haskell itself besides executing the function to give it some unique id. Last problem for me in haskell solved, i should be happy.

As far as i understand it now is, that the haskell compiler can't look into the functions written in c and thus does not know what they will return with which input value, thus the created program has to execute them every time. Monads and similar stuff (Arrows) just make sure, that we use a return value only one time.

Only problem is a runtime environment, which could predict from the last input values the output values of a function and replace its call with the result without executing anything.

Name: Anonymous 2008-09-26 8:03

>>57
Let's implement side effects in Haskell without using Monads. Haskell is a pure language, so all side effects must be explicit. To do that we first define a datatype
data World = World ...
World contains all the state of the runtime environment. Now if we want to write a function that modifies this state, we must pass the state to the function and then it returns a value and a new state. So we would define getChar as
getChar :: World -> (Char, World)
and putChar as
putChar :: World -> ((), World)
putChar doesn't have any return value so we return () which is just the same as void in C.

Now we want to use these function to write a function cat, which copies it input to the output. cat has side effects so it gets a state as a paramater and returns () and a new state.
cat :: World -> ((), World)
cat s0 = let (x, s1) = getChar s0
         in if x == EOF
            then ((), s1)
            else let (y, s2) = putChar s1
                 in cat s2


You can probably see that this explicit passing of state can get ugly real quick. Monads allow us to hide this. We define a datatype IO as
data IO a = IO (World -> (a, World))
which is any function which has a side effect and returns a value of type a. So now our getChar and putChar are defined as
getChar :: IO Char
putChar :: IO ()


To make IO into a Monad we must implement the functions of >>45.
instance Monad (IO a) where
  IO m >>= f = IO (\s0 -> let (x, s1) = m s0
                              IO m' = f x
                          in m' s1)
  IO m >> IO m' = IO (\s0 -> let (x, s1) = m s0
                             in m' s1)
  return x = IO (\s0 -> (x, s0))


Now we can write our cat function as
cat :: IO ()
cat = getChar >>= (\x -> if x == EOF
                         then return ()
                         else putChar x >> cat)


Or using the do-notation as syntactic sugar
cat :: IO ()
cat = do x <- getChar
      if x == EOF
         then return ()
         else do putChar
                 cat

Name: Anonymous 2008-09-26 8:47

FUCK  OFF  ALL OF yoU THIS ISN"T REDDIT
sage

Name: Anonymous 2008-09-26 11:03

>>58
Copy pasta? Or are you retarded?

Name: Anonymous 2008-09-26 11:21

>>49
2) There's no substitution, it's all Haskell.
3) I've never seen anything like that happen. An example would be great.

>>49,57
You know, if you look at ther source code of the monads, all your doubts will vanish.

Name: Anonymous 2008-09-26 11:59

>>61
>You know, if you look at ther source code of the monads, all your doubts will vanish.

I did that and yes, IO Monad uses RealWorld. But until i analyze every element of the source, i'll stay with the explanation in >>56 , which catches enough for me.

Name: Anonymous 2008-09-26 12:15

I'd like to look at the source code of Leah Culver's monads, if you know what I mean.

Name: Anonymous 2008-09-26 12:35

>>63
I see what you did there.

Name: Anonymous 2008-09-26 13:01

>>63
Did you mean: Leah Culver's gonads

Name: Anonymous 2008-09-26 13:41

>>56
Do you think so much complexity is really worth it, when we could be using a language as simple as, say, Scheme?

Name: Anonymous 2008-09-26 14:03

>>66
It's not actually complex, and you have to try the language yourself to really answer that question. My personal opinion, though, is that Haskell is indeed very much worth itsage.

Name: >>67 2008-09-26 14:04

Oops, misplaced my sage.

Name: 56 2008-09-26 14:16

>>66
Putting up with the endless contortions of Haskell's type system in search of a meaningless standard of purity doesn't make a lot of sense, but locking yourself in a small white room made of fuzzy parentheses isn't productive either.  I stick to practical languages; preferably those made for extraction and/or reporting.

Name: Anonymous 2008-09-26 14:22

>>58
Haskell is a pure language, so all side effects must be explicit.
Proof that all Haskell users are on drugs.

Name: Anonymous 2008-09-26 14:24

>>69
I don't feel a complex type system is the pinnacle of purity. To me, dynamic typing feels far nicer.

Name: Anonymous 2008-09-26 14:42

>>71
How is Haskells type system complex? I think it's pretty simple and straightforward and because functions and types work together in a natural way, you can write concise programs.

>>70
No, just that they care more about correct program behavior and proofs and don't want their computers fucked up because of some nasty memory bug.

Name: Anonymous 2008-09-26 14:53

>>72
No, just that they care more about correct program behavior and proofs and don't want their computers fucked up because of some nasty memory bug.
But where are these awesome Haskell programs that perform correctly and solve all the world's problems? It just happens to be that I stopped using the only Haskell program I've ever found even remotely useful, darcs, after I found out that it systematically chokes on even the most elementary operations*.

* Yes, it didn't fuck up my computer because of some nasty memory bug, but I favour programs that actually do what I want, when I want.

Name: Anonymous 2008-09-26 15:12

>>73
1. Read YAHT.
2. Rewrite a program in Haskell, preferably one you wrote.
3. ???
4. PROFIT!

Name: 72 2008-09-26 15:31

>>74
Strangely enough, I've done exactly that a year ago or so (yes, for real). The lack of rudimentary libraries made it quite a terrible experience.

Anyway, that has nothing to do with my point.

Name: Anonymous 2008-09-26 15:40

>>75
Rewrite some other program that doesn't require said rudimentary libraries.

Name: Anonymous 2008-09-26 15:44

>>76
>>75
Anyway, that has nothing to do with my point.

Name: Anonymous 2008-09-26 15:48

>>77
Your point won't matter to you after you follow >>75,76's advice.

Name: >>78 2008-09-26 15:50

* >>74,76's advice

Name: Anonymous 2008-09-26 15:59

>>76
Is this just your way to say ``write just another fib or fact like every other Haskell programmer''?

Newer Posts
Don't change these.
Name: Email:
Entire Thread Thread List