1. 19

    I’ve seen this argument a lot that you CAN do one in the other, however syntax matters and defaults matter.

    1. 3

      Case in point:

         (assoc map :key value)
      

      In JavaScript:

         Object.assign({}, {key: value})
      

      Which is both more complex, less obvious and less efficient.

      1. 2

        Redux apps can use ES6 spreads for this: { ...map, key: value } - less efficient but certainly not too onerous syntax wise.

        1. 1

          This is not ES2015 (ES6) but ES2017. ;)

          1. 1

            Actually, it is not standardized at all. It is still a stage 3 proposal.

            https://github.com/tc39/proposal-object-rest-spread
            https://github.com/tc39/proposals

        2. 2

          Would anyone do that in real JS? (I don’t write JS, but if the answer is “no”, then I don’t see the point)

          As time goes on I have to admit that FP hype gets on my nerves. I enjoy the functional combinators as much as the next person, I love getting work done in Erlang, I am sometimes grouchy when writing Go when I can’t just map over a container, I love testing pure functions in any language, but maybe it has been python and rust that have made me a little happier in general to fall back on the boring procedural control structures (they support both paradigms, and yet people tend to use explicit iteration instead of the combinators pretty frequently). Readability is nice.

          1. 5

            Would anyone do that in real JS? (I don’t write JS, but if the answer is “no”, then I don’t see the point)

            Can’t speak for others, but we do that a lot in our React/Redux app to avoid mutation of objects from spreading.

            I have been using Python in a functional style, with LCs, map, filter and just about everything from the itertools and operator modules, but it was just not idiomatic. So when I switched to Clojure where this is the dominant way to do things it feels like coming home. I think the procedural control structures, especially when used in places where a map or fold would suffice makes it more difficult to understand what is going on because they could do anything.

            1. 3

              You might be interested in Coconut (http://coconut-lang.org).

              1. 1

                We should use the abstractions that minimize incidental complexity. I like using combinators when they fit on a single clean line. I tend to get lost when reading code that nests them, or is like a chain of 4+ combinators that hasn’t been documented more thoroughly than average. While I enjoy writing clojure and erlang (languages heavily reliant on combinators) they tend to be languages that I despise reading other people’s code for the most. I’m happy when people spend the time to make their stuff clean and fucrs-compliant, but it’s so damn painful for me to follow a nasty chain of nested combinators.

              2. 2

                Oh yeah, I have a React/Redux project that sometimes felt like half my code was calls to Object.assign. It’s the easiest way to do a shallow copy of an object so you’re not inadvertently passing references to the same object around and mutating them.

                Python does cause you to use more of the “boring procedural” control structures, and it does nominally support some functional programming, but some of it is more because of inconvenience than anything else. For example, I write far too many nested for/if loops where filter would be more natural if filter/map/lambda was less clunky and faster. I don’t think this makes it easier to read. I also think its reliance on list comprehensions is wrongheaded, because even now, after knowing Python for… ugh, nearly twenty years… I can never remember the order for iterating through nested lists in a list comprehension.