Live data from Hacker News

Two Vexing Problems in Functional Programming

matthewbutterick.com

191–200 of 217 posts

Re: Two Vexing Problems in Functional Programming

#191
post #121

Earlier quoted context omitted.

> you want to modify a list - how do you know if the inner list changed or not You know for sure that inner list did _not_ change, because it is immutable. Someone else might have a reference to an updated hashtable with an updated inner list, but the one you hold will never change—isn’t that the whole idea of immutable data structures?

No, I mean "update" in the persistent sense - create a new list, with some (or none) elements changed/added/removed. e.g. say you have a method remove_all_in_values that takes an int x and a hashmap of list of int, and returns a new hashmap of list of int, with x removed from each element of the hashmap. Obviously you'd use something like List.filter for the inner operation, but most functional programming languages…

I see what you mean now.

I think most persistent data structures would (for most common operations) return exactly themselves in case when no modification happened. So you can very cheaply compare for equality, and that would either resolve to simple one-op comparison of references (to see if they are equal or not), or, in the worst case, comparison of some minor amount of diverging sub-elements (since persistent data structures do extensive structural sharing by definition).

In this sense, linked list is a “bad” persistent collection for your use case, but a persistent set instead would work wonderfully — if nothing changed, you’d get the same reference to a collection as input.

I am pretty sure it either would work this way, or is very easy to optimize for this use case, in Clojure.

Re: Two Vexing Problems in Functional Programming

#192

Personally I never really understood the benefit of thinking in functional terms about things that are conceptually more naturally thought of as persistent objects. For example when the author picks "parents" or "children" or in general maybe any entity of any kind, I don't understand what functional thinking gets me. Sure instead of manipulating mutable objects I can think of every entity being 'one thing' at 'one m…

> Personally I never really understood the benefit of thinking in functional terms about things that are conceptually more naturally thought of as persistent objects.

Like the vast majority of software developers world wide, who just want to get things done and/or earn money.

The simple truth is: A minority prefers purely functional programming. The vast majority prefers procedural programming with functional elements.

For some reason, those who prefer pure functional programming often try to convince everyone else their way is the best way in an obnoxious way.

Re: Two Vexing Problems in Functional Programming

#193

Earlier quoted context omitted.

The computer is not an imperative machine. It's a physical machine that you describe with an imperative representation in your mind. Can you tell the difference, or are you unaware of the map-territory distinction going on? Functional programmers are simply choosing to use a different style of map, but we both represent the same reality.

According to Wikipedia, "the hardware implementation of almost all computers is imperative." https://en.wikipedia.org/wiki/Imperative_programming

[Citation needed]

Re: Two Vexing Problems in Functional Programming

#194

You should not approach problems in functional languages with imperative techniques. It's fitting a square peg in a round hole. The approaches & data structures aren't always the same. In my experience with FP you start with more of a top down approach in contrast to the bottom up approach discussed in the blog post. There are many good resources on this. I've referenced a few below. Of course there are many more. [1…

I think anybody who wants to understand Functional Programming should start with Lambda Calculus.

I highly recommend An Introduction to Functional Programming Through Lambda Calculus by Greg Michaelson.

You can then see how to express Functional Techniques in your language of choice (i.e. one you already know well eg; Functional Programming in C++ by Ivan Cukic) before learning a new Functional Language. This is to avoid the confusion in syntax/semantic expression of unfamiliar concepts which is a bit too much for a beginning student to handle simultaneously.

Re: Two Vexing Problems in Functional Programming

#195
post #116

Tangential but what is the most successful and most complex example of a fully FP-based application where I can view the source-code today? I feel like I still don't quite grasp the essence of the conflict between FP and whatever it seems to be opposing. I also feel like I use what a lot of FP people claim as FP in my day-to-day. I think if I can see some code beyond the old map/reduce toy examples it might click. No…

https://news.ycombinator.com/item?id=30878534#30888405

Re: Two Vexing Problems in Functional Programming

#196
post #97

Earlier quoted context omitted.

> This is especially bad if you want the data structure to be shared across multiple threads. Just iterating over a tree now requires taking and releasing oodles of locks. Um, what? Persistent data structures don't require locks at all (because they're immutable), in fact using them in a multithreaded way is 100% safe and thus much easier than their mutable (and ordinarily more efficient) counterparts.

Refcounted gc means you need locking on refcounts or you can lose your tree during iteration.

Can you provide a list of reference-counted functional languages?

Re: Two Vexing Problems in Functional Programming

#197
post #121

Earlier quoted context omitted.

No, I mean "update" in the persistent sense - create a new list, with some (or none) elements changed/added/removed. e.g. say you have a method remove_all_in_values that takes an int x and a hashmap of list of int, and returns a new hashmap of list of int, with x removed from each element of the hashmap. Obviously you'd use something like List.filter for the inner operation, but most functional programming languages…

You can pretty efficiently do this in Clojure (update-in {:foo [{:bar ["a"], :baz ["b" "c" "d"]}]} [:foo 0 :baz 1] clojure.string/capitalize) ;; => {:foo [{:bar ["a"], :baz ["b" "C" "d"]}]}

This only works if you know what to edit up-front.

If you're processing a tree-like structure via recursion (e.g. type-checking an AST implemented with persistent immutable structures in a compiler) it's no longer easy.

Re: Two Vexing Problems in Functional Programming

#198

Earlier quoted context omitted.

Not really arguable, IMO. Just because both lambda calculus and assembly are Turing complete does not mean that CPU architecture isn't clearly imperative.

How do you define "imperative" in a way that precludes a functional description of your definition? I'd say that if you're able to do that, you'd have found a contradiction in Turing completeness and win you a Turing award. Also, this: https://news.ycombinator.com/item?id=30883863

Just because every program in C is also expressable in Haskell does not mean that C is Haskell or that C is a functional programming language.

The same is true of CPUs, which at their base level execute instructions line-by-line to move and load things in and out of stateful registers as well as doing simple mathematics.

Not going to keep arguing, as I can see from your other comments that you are going to try to hold this line, and also your reasoning doesn't really make sense.

Everyone has heard of Turing completeness. It does not imply that all distinctions between the semantics of languages and the structure of hardware thus are collapsed. It means that you can write an equivalent program using different semantics or different hardware.

Re: Two Vexing Problems in Functional Programming

#199

Personally I never really understood the benefit of thinking in functional terms about things that are conceptually more naturally thought of as persistent objects. For example when the author picks "parents" or "children" or in general maybe any entity of any kind, I don't understand what functional thinking gets me. Sure instead of manipulating mutable objects I can think of every entity being 'one thing' at 'one m…

Rich Hickey made a great talk on this in 2009 https://youtu.be/ScEPu1cs4l0 An other way to think about it is that the programs we write do not literally simulate entities (users, other domain objects like books, students, professors, classes, etc). Our software simulates the record keeping devices that store /protect information regarding these entities. We are most of the time writing information processing systems,…

*without forgetting the old.

Re: Two Vexing Problems in Functional Programming

#200
post #124

Earlier quoted context omitted.

Translating naively, in Haskell I might use https://hackage.haskell.org/package/containers-0.6.5.1/docs/... , which does use sharing to reduce copying.

A simple Brankfuck interpreter in Haskell using state monads may be found at https://tromp.github.io/cl/Binary_lambda_calculus.html#Brain...

Yeah, for something where changes are local like that, using two stacks for your tape makes a lot of sense.
Post reply on HN