My problem with all that |>-ing is naively we'd define map as
| map :: (a -> b) -> [a] -> [b]
|
which, again naively, appears to be producing a new list every time it is called, which we would rather not do when it is part of a larger chain of intermediate steps. in haskell this is supposed to just work because everything is evaluated lazily. but sometimes this doesn't just work, maybe because of some terrible graph reduction edge case that requires a masters degree to understand and 800 megabytes of memory to evaluate*, or because [] is a linked list internally and maybe you really want some other abstraction pulled from category theory to better express what you are doing, and then later you discover that Real Haskell Programmers pepper their code with strict annotations and they know never to define map in such an amateurish way anyway
but that's just Haskell. I don't know about F#, but rust ofc does everything with iterators, so what you get back from map and filter is not a new array but an iterator that's yet to have its lever cranked. clojure solves this problem yet another way with transducers, which is really the same thing but uses higher order functions instead of iterators to get some brownie points about being stateless
basically by and large in the functional world your classic examples of functional code--by which i more or less mean expressing data transformations as morphisms, so x.map().filter().andSoOn() can become compose(map, filter, andSoOn)(x) for 'free'--do not do what they purport they do; they also, and sometimes only, prepare the machinery required to make the transformation happen. and its a lot of machinery, and its different for every language, and it will bite you in the ass if you don't understand it (and web programmers
by and large don't). So its just no silver bullet all over again (oh, one thing i hear, about programming '
in the problem domain and not the solution domain'--already has collapsed for FP, let alone OOP, which has since moved from being the problem domain to the new solution domain)
But! This is all very little compared to what I wanted to get to in the first place, which is I do not mind the difference between
| sum(map(square, filter(odd, x)))
|
and
| x |> filter odds |> map square |> sum
|
simply because the first is much closer to the natural language way of expressing it, "sum the square of each odd number in x," than the second, which is a sequence of high-level instructions that happens to create the desired output. something of a taboo in fp as i understand it, the frisson of the imperative, ah,
anyway with currying you can see at a glance that the last term, x, can be pulled out to make it point-free. |> just complicates things in that context, although it obviously has its uses
*understanding seq in haskell is probably a bit like understanding pointers in C