8 comments

[ 3.8 ms ] story [ 33.2 ms ] thread
There's something beautiful about function composition. Great to see it in another language (me coming from JavaScript).
To be honest, I'd struggle to think of a language with generics or dynamic typing where you couldn't do function composition.

Even in C, you could do something like in this godbolt link (ugly, I know):

https://godbolt.org/z/aKTz6fdbc

That's not quite the same (functionally) as the Rust solution though? Unless you meant to just illustrate a minimal PoC, in that case I suppose it does the job. More importantly (IMO) Rust allows us to be truly generic without sacrificing any type safety in the process.
«I actually thought I knew rust until I read that» — the article anticipates the reader's feelings pretty well %)
This is interesting, as a Haskeller interested in type geekery who doesn't know Rust. I can't promise anyone else would find it interesting.
Is the Rust compose backwards? Normally I would expect compose(f,g)(x) = (f∘g)(x) = f(g(x)), but in this post it's g(f(x)).

In Haskell for instance,

    (+2) . (*10) $ 2
    => 22
This is purely notational convention and both interpretations are pretty widely attested in different subfields. The composition circle operator is most often the Haskell order (“f after g”), but “compose” can refer to either.
Haskell's compose being in that direction ends up fairly annoying, IMO. That's not the direction we think about a chain of functions, 90+% of the time, so you end up having to type the next thing in the chain, then go backwards over everything you just typed to do the next step.

Thankfully in Haskell you can just define your own, but it's annoying and then harder to share than if one existed in prelude. IIRC (<<<) or one of them is a more general backwards compose, but the precedence ends up working poorly so it's not a good fix.