Hacker News new | ask | show | jobs
by anyfoo 1602 days ago
My experience:

For one, it makes reasoning about runtime (as in "how long") harder: E.g. an innocent looking "take 5" might be what actually executes half of the code you've written... which is also harder to reason about than if it would be "all of it". This can also make debugging harder: Values are only evaluated when they are needed, and a "value" itself may not be just, say, a single number, but a complex data structure consisting of many values, so that "evaluated" has many different stages between "a thunk, not evaluated at all" and "weak head normal form". So code does not get executed when you wrote so in your program, but potentially much much later. Semantically that should not make a difference (the results should be the same), but when you want to debug program flow...[1]

You can see how "thunks" in general add a certain dimension to everything you do. Throw in interaction with garbage collection, and things aren't always obvious in resource usage.

Also, there is maybe an argument that if you have infinite data structures that you only tend to evaluate partially (which is what makes laziness really fun, actually), then accidentally trying to fully evaluate such a data structure makes your program not terminate anymore. But I'm not sure how that's really a problem coming from laziness. Laziness allows you to handle infinite data structures in the first place, mishandling them is not much different than accidentally writing an infinite loop in a strict language, in my opinion.

That being said, I still enjoy writing Haskell very much when I get to. It makes me feel much more productive, and I do lament having to use other languages at work. I must say using Haskell was always on private projects, and I have never tried doing so in a team, though.

[1] On the flip side, I find the pureness and strictness of Haskell to make debugging easier, or just less necessary.