Live data from Hacker News

List is a monad

alexyorke.github.io

121–130 of 187 posts

Re: List is a monad

#121
post #5

As far as monad tutorials go, this one seems quite good. I like the categorization of monads between "containers" and "recipes". However, I personally think that monad tutorials tend to give people the wrong impression and leave them more confused than they were before, because they focus on the wrong thing. A monad is not a complex concept, at all. IMO a more useful way to present the topic would be with one separat…

If all monad instances work differently what is the value of the Monad interface? What kind of usefull generic code can one write against the Monad interface. Related: https://buttondown.com/j2kun/archive/weak-and-strong-algebra...

> If all monad instances work differently what is the value of the Monad interface? What kind of usefull generic code can one write against the Monad interface.

Code that composes a bunch of operations, for whatever kind of composition those operations need (some people call Monad "programmable semicolons", because it's a lot like sequencing). E.g. traversals of datastructures, or some kind of "do this in a context" operation. Essentially any function you pass a "callback" to should probably be written in terms of monads so that it can accept callbacks that need different kinds of composition beyond just being called at different points in the control flow.

Re: List is a monad

#122
post #17

Earlier quoted context omitted.

If all monad instances work differently what is the value of the Monad interface? What kind of usefull generic code can one write against the Monad interface. Related: https://buttondown.com/j2kun/archive/weak-and-strong-algebra...

Your basic problem is that your programming language can’t express the concept cleanly. You need what’s called “Higher-Kinded Types”. To give you a concrete example, in C# Func , List -> List Func , Task -> Task Func , Func -> Func Can’t be expressed using a generalisation. But in Haskell, you can write (Functor F) => Func , F -> F One of the biggest things that makes monads hard to understand is that the type system…

I'm sorry, I'm not sure I understand entirely what you are trying to express by

  Func, List -> List
That said, in C#, you can write:

  List listA;
  Task taskA;
  Func func;
  
  List listB = from i in listA select func(i);
  Task taskB = from t in taskA select func(t);
And if it can resolve a method on List called 'Select' that takes a Func that returns a List, and a method on Task called 'Select' that takes a Func that returns a Task this will compile.

In other words, I kind of think that Select methods (which can be Select extension methods, of course) amount to functors in C#?

Re: List is a monad

#123

The obsession with trying to explain a monad ultimately stems from conflicting explanations and the inability to differentiate between a mathematical monad and monads implemented in software. Monads in software are just a standard API for any given type. That’s it. Theres no magic here. Just implement the standard and you have a monad. It grinds my gears seeing monad tutorial after tutorial using the wrong metaphors…

Associativity is important, and not something that can be expressed in the API in most languages.

Re: List is a monad

#124
post #5

As far as monad tutorials go, this one seems quite good. I like the categorization of monads between "containers" and "recipes". However, I personally think that monad tutorials tend to give people the wrong impression and leave them more confused than they were before, because they focus on the wrong thing. A monad is not a complex concept, at all. IMO a more useful way to present the topic would be with one separat…

I came to the conclusion that a List is a good generic data structure, for instance in cases where the cardinality is supposed to be 0..1 it is often less trouble than a nullable scalar or an Optional and you have cases where you’re going to get a list anyway such as if you are querying a relational database. (Often people write awkward code to turn that result into a nullable/Optional and then more awkward code to turn it back to a list later) Lists work almost exactly the same in most languages whereas there is often something weird about null, there might not be Optional, it might have something weird about it, etc.

For multi-language distributed processing, particular if JSON is involved it’s worth a try.

To be fair I write a lot of Java where Optional is a train wreck in so many ways not least it could be null anyway, you are allocating objects needlessly, and I just see people get hypnotized by awkward code also they write bugs or scan right past them.

Re: List is a monad

#125
post #101

Monad tutorials are on the rise again. Let's start with function composition. We know that for any two types A and B we can consider functions from A to B, written A -> B. We can also compose them, the heart of sequentiality. If f: A -> B and g: B -> C then we might write (f;g) or (g . f) as two different, equivalent syntaxes for doing one thing and then the other, f and then g. I'll posit this is an extremely fundam…

Thank you so very much. This is the first time monads have made sense to me, and now its clear why. People who try to explain them usually end up adding all kinds of Haskell minutia (the top post is another example), rather than actually explain the concept and why we need it. Your comment is the first time I actually understand what it is, and why it might be useful.

Re: List is a monad

#126
post #112

Earlier quoted context omitted.

This is like explaining chess by simply stating the rules. Like sure explaining the rules of chess is important but only knowing the rules provides for nothing more than a superficial understanding of a topic.

I mean if someone is learning chess for the first time, then yes you should start with the rules rather than jumping right into waxing philosophic about positional strategy to show off how smart you are.

I think the point is that a monad is a useful concept _purely_ because of what it _allows_ you to do, and _not_ because of anything syntactical. Those rules that you're obviating there, the commutative squares, are precisely what then lets us have powerful intuitions about these objects. The type signatures matter a lot less. If, for example, you don't have functoriality (which is false for `std::vector`, for instance, since `std::vector` is special-cased) you lose the ability to reason powerfully about abstract algorithms.

Thus, explaining the syntax and where the type variables go is explaining the least relevant thing about monads to their power and importance. It's certainly easy to showcase both the syntax and the list and maybe monads, that's part of the "monad tutorial fallacy". Gaining intuition for how to think about monads _in general_ is a lot harder and requires practice. Like, yes, list and maybe are "containers", but is `(->) t` a container? Is `IO`? How do these compose, if at all? What is this about "effect" semantics, "I thought monads were just burritos/containers"? etc. These are the hard, both conceptually and pedagogically, questions. Yes you need to know the syntax to use it in any given programming language, but knowing what scabbard your knife fits in doesn't give you the skills of how to use knife :)

Re: List is a monad

#127
post #5

As far as monad tutorials go, this one seems quite good. I like the categorization of monads between "containers" and "recipes". However, I personally think that monad tutorials tend to give people the wrong impression and leave them more confused than they were before, because they focus on the wrong thing. A monad is not a complex concept, at all. IMO a more useful way to present the topic would be with one separat…

I found helpful. It really clarified a few things for me.

Re: List is a monad

#128

The way I think of it, monads are a solution to Callback Hell, where you've fallen in love with lambdas, but now you have a nightmarish mess of lambdas in lambdas and lambdas calling lambdas. The monadic functions allow you to create "for comprehensions" aka "do comprehensions" but really, they look like a classic for-each loop. They secretly call the monadic map/flatMap/filter functions. for x in list doThings(x) Th…

After reading your comment, I've made it my mission to understand it. Although I have no idea what you're talking about, you make it sound intriguing.

You might like https://philipnilsson.github.io/Badness10k/escaping-hell-wit... which is a longer version of the same kind of argument.

Re: List is a monad

#129
post #80

A monad is not a container! It’s a way of composing functions if they have an effect. You tell how to inject a value in that effect (unit) and how to compose two functions that have that effect and that’s it: programmable semicolons.

Thanks for the feedback, I totally agree that monads are not containers. From an OOP perspective, they have some properties that make them, in some sense, sorta like containers, e.g., they contain a value like the Maybe monad. I still agree that they are not simply containers. I can clarify this in a revision to part 1 soon.

> From an OOP perspective, they have some properties that make them, in some sense, sorta like containers, e.g., they contain a value like the Maybe monad.

Not always! I find this is a big source of confusion; not all monads contain values, sometimes beginners think they can or should "get the value out" of a monad and that tends to lead to writing the wrong kind of code.

Re: List is a monad

#130
post #76

The amount of people who tie themselves into knots to understand this pointless concept is very funny to me. I am 16 years into a successful software engineering career without learning what a monad is an it never held me back. Turns out I can use lists and optional types and all that jazz without it. I mean really. Look at posts like this[0]. What does this give you? Nothing, in practical reality. Nothing. [0] https…

> I am 16 years into a successful software engineering career without learning what a monad is an it never held me back.

How would you know? That's the classic Blub Paradox.

Being able to write a custom monad and then leverage the vast array of libraries that already exist has helped me deliver functionality to end users quicker, more maintainably, and with lower defect rates. They don't let you do anything that you couldn't do by writing it out longhand. But just like using generic container libraries instead of writing a specific container for every type you want to handle collections of, they're extremely helpful.

Post reply on HN