> Basically, the author's criticism is that the language is too powerful, too expressive, people try very abstract things
I think this is a bit unfair. The author's criticism is that people try very abstract things and don't stick the landing. And to an extent I agree, but the problem isn't that Haskell is too powerful, it's that it's just barely powerful enough for too many things. Contra the author, GADTs are not one of those things, and snoyman can pry them from my cold dead hands. But singletons clearly are. So are impredicativity, open type families, type level arithmetic, and Template Haskell. Idiomatic Haskell practically writes itself, but type-level Haskell is at least as hard as C, and it's almost entirely because of how terrible the ergonomics are.
> Third, about backwards compatibility
Strongly agree here, if anything GHC doesn't break backwards compatibility enough. `Num` is an abomination.
I think one of the problems that people who get overexcited about functional languages and all the strong typing and such have is that they generally start out in a bad place. Imperative programs with every flaw in the book, threading by locks, for loops that try to modify the index mid-loop, mutation running rampant, all the bad things they complain about. I've worked in those code bases in industrial contexts, they can be nightmares for sure.
So they discover functional programming, and they just get hammered with so very many different ways of doing things. At first it all seems impossible, but then it slowly unlocks itself, and look! All the problems with imperative programs went away! You didn't even properly perceive them before, but they're gone.
You can't hear me, so my tone here is completely serious. I strongly recommend any professional programmer spend some time with a language like this and attain enough fluency to write real, non-trivial code in it, not just map a few lists and maybe use a monad or two. Get something that hits the network or something.
And the problem is, too many of them stop here. Conventional programming sucks. Functional programming rules. Anyone who doesn't use functional programming languages is a loser still wandering blind in the wilderness.
However, there are in fact a lot of practical problems with functional programming languages too, many in the original blog post, others expressed elsewhere. It can be as simple as, that critical library I need is not available in my obscure niche functional programming language, but alas, in the real world, that's enough to be a determining factor.
Where the religious-level advocates of FP lose contact with reality is that there's a third option: You take what you learned in the functional programming world and come back into conventional languages. And I don't mean "use a few maps and jam a monad in to your language even though it completely fails to fit"; that's actually still completely missing the point of functional programming. I mean, you start writing "conventional" code except you pay attention to mutation. You may not write completely pure code everywhere, but the more you mix in the more characteristics of pure code, the more of the benefits you get. (I do think there's an interesting discontinuity at 100% pure, when you can 100% count on it and then build further on that ability to be sure all code is pure, but you do still get a gradient of benefits the more purity you put into your conventional code.) You pay attention to side effects and start isolating them into units instead of mixing them in. You learn how to multithread with messages instead of memory sharing and locks. You don't drag in inappropriate APIs from a foreign paradigm; you take the fact your eyes were opened, and you write code with those now-opened eyes.
And it is not perfect. You will still occasionally have the original imperative problems. But you will have radically, radically fewer of them, so few that the cost/benefit analysis of using the super-strong stuff becomes very difficult to justify, especially over the advantages of being able to use that library you really need. (And see the library has a mutation problem and wrap it in a way that solves it for you, instead of letting it drag the rest of your code base down, etc.)
I have ridden the mighty moonworm... errr... I have fiddled with the Haskell type system and done some interesting things with it. But by and large they really weren't worth it, not in the sense that they don't solve some problem, but in the sense that back in the conventional programming world, I really don't have those problems anymore. No credit for solving problems I don't have.
This is where I diverge with people complaining about not using functional programming. They are comparing writing imperative crap with writing pristine functional code. In this context I don't deny I'd take the functional code too. But I am comparing writing eyes-open conventional code with writing normal functional code. In this context the advantages are a great deal more muted and it isn't anywhere near the day-or-night level of difference... and I gotta say, pitching me back on full-on functional programming by claiming I just don't get it and I just want to write bad code and enable bad code and in general be lazy and bad is bad advocacy in almost every possible sense of that term.
I apologise for the comparison, as your thoughts are very well-structured, and in my head it almost sounds like an insult. But this kind of thinking ("more discipline minimises the problems related to suboptimal languages") is kind of like Uncle Bob's test-zealotry - i.e. you don't need static typing/AOP/linting/any kind of bug-reducing feature, because you can just write more tests (even if it's painful or spurious)
Sure, it is possible to be very disciplined, avoid messy control flow, be careful with mutation, etc.... then good luck trying to get everyone else to get on board with a very niche coding style, unless if you have the strict authority to enforce it. Sadly, in most cases you don't, so you are stuck with the non-verifiable madness.
In an ideal world, this would work - but in an ideal world, we would also be using better languages with way better guarantees and compile-time checks.
I don't really get your point, other than trying to insult everyone. It's fairly well established that in the real world, strict functional programming languages aren't an option. So who really cares that you keep railing on about them? Until they're an actual option, we are not being "zealots" when we can't use them... not "refuse" to, can't... and, yes, you're just being an insulting jerk with no real options to offer anyone.
If you want to be wistful for a world where we could use better languages... get in line. It's a long one. But stop expressing it in the form of insulting other people.
You are not the smartest in the room, you are not the only one who has grappled with the issues, and if you'd stop going out of your way to insult everyone else, maybe you could listen to and learn from people offering solutions. Even if they aren't perfect; it's hardly as if you're offering a perfect one either. You aren't offering one at all.
Sure, but if we are talking about a place where let's say functional programming is off-limits entirely (note that I wasn't strictly talking about functional programming in my previous posts; I was talking about anything, any paradigm or tool which helps write more sound, more provable, more stable and less buggy programs)... then the "discipline yourself and enjoy the benefits of FP in less capable languages" will not work either, because in that place, they clearly don't recognise the benefits, the language doesn't encourage it either, so they'll just write the average code as usual.
I am not insulting people personally, I am insulting the "worse is better" culture which is prevalent in the profession. No one has an immutable opinion about this, and I do not think that looking down upon an opinion or set of beliefs is a hostile thing. In a (slightly weird) way, it's actually constructive because it might plant a seed of thought in people that it's possible to do better. I'm doing the opposite of looking down at or insulting people here - I am assuming they are rational and capable of thinking, they just haven't encountered a different mindset than the prevalent and trendy one, and that's a perfectly fine thing.
"Developing/using better tools, languages and trying to change developer culture" is a solution. Sure, not a silver bullet or something achievable quickly or easily, but on a smaller scale, it's definitely possible to achieve success.
> And it is not perfect. You will still occasionally have the original imperative problems. But you will have radically, radically fewer of them, so few that the cost/benefit analysis of using the super-strong stuff becomes very difficult to justify, especially over the advantages of being able to use that library you really need.
This has unfortunately not been my experience. Working alone, sure, I can write acceptably pure code in a conventional language. But generally the issue isn't what I can do, it's what my coworkers will do. Even if almost everyone manages to maintain strict discipline without the support of the language, it really only takes one "productive" cowboy to create a disaster. The biggest advantage of pure functional programming is that taking the path of least resistance produces code that's still sort of ok.
I think this is a bit unfair. The author's criticism is that people try very abstract things and don't stick the landing. And to an extent I agree, but the problem isn't that Haskell is too powerful, it's that it's just barely powerful enough for too many things. Contra the author, GADTs are not one of those things, and snoyman can pry them from my cold dead hands. But singletons clearly are. So are impredicativity, open type families, type level arithmetic, and Template Haskell. Idiomatic Haskell practically writes itself, but type-level Haskell is at least as hard as C, and it's almost entirely because of how terrible the ergonomics are.
> Third, about backwards compatibility
Strongly agree here, if anything GHC doesn't break backwards compatibility enough. `Num` is an abomination.