Hacker News new | ask | show | jobs
by kyllo 2553 days ago
You sound smart, but I don't want to have to be that smart when I'm refactoring code. I want the compiler to do as much thinking for me as possible. I want to be able to change it in one place and have type errors to remind me of any other places in the codebase I forgot to change.

Static analysis doesn't solve all your problems, but it solves enough of them to be a very useful technique.

1 comments

Static typing cannot ensure about their code what the coder can and should ensure about their code.

And often -- very often -- especially in strongly typed languages -- the static checker will reject code that is otherwise valid. First point.

Second point: Statically typed PLs (especially strongly typed ones) enforce the verifications across the code, with no (at least non-ridiculous) way for the coder to be judicious about things.

Third point: statically typed languages have weaker runtime features/abilities: polymorphism, homoiconicity, true REPL (ie true read->eval), etc.

All of these points add up to MORE cognitive complexity for the coder who is trying to develop non-trivial business applications -- not less cognitive complexity.

It's not being smart. It's learning. Once you learn algebra, say, many classes of problems without algebra would be too much cognitive complexity.

Type systems are focused on one thing: type coherence. But the real world demands runtime dynamics are what the customer is paying for; being as close to that need as possible IS lower cognitive impedance.

"enforce the verifications across the code" is the point.

I've worked with a ton of Python code that looks like this:

    def foo(bar):
        # do stuff
        return baz(bar)
What does `foo()` return? I have to go read the body (or docstring if I'm lucky) of `baz()` to know that. And `baz()` might be another level of indirection to `quux()`. If I change what `baz()` returns, now I need to grep my codebase for all call sites of `baz()` and verify that the new return type is acceptable at each of them, and make changes if not. This is super time-consuming and error-prone, especially when a compiler (especially with an IDE refactoring tool) could do take care of it for me in seconds. It's easier if I have a good test suite, but that means I'm just implementing static type checking with runtime tests, which is more code that I have to maintain.
You're looking at this Python code and blaming its deficiencies on lack of types. It's deficiencies are not lack of types, but lack of separation of stable vs volatile code, lack of contract specification and documentation, lack of refactoring and versioning idioms (see https://www.youtube.com/watch?v=oyLBGkS5ICk).

Why does the blame always go to lack of types?

Whether or not you have types you're still going to suffer if you don't have the other things I mention. And if you have the other things I mention then static typing become much more of a nuisance. Ergo...