Hacker News new | ask | show | jobs
by toolz 949 days ago
I'm firmly in the camp that it's all perception. The studies I've seen aren't what I would consider conclusive, but they certainly suggest there is very little difference in the output and bugs of dynamic vs static languages.

In my experience, static typing seemed to lend itself to poor testing, maybe some sort of belief that static types were good enough to not need tests that can prevent regressions. So from my point of view the static typing is negative value. It prevents such a low value class of bugs while seemingly incentivizing people to be lax with the most important classes of bugs.

1 comments

I literally struggle to read and work with dynamic code. My head explodes when trying to hold return types or the shape of semi-complex data structures in my head, versus having it spelled out. I wouldn't call it an issue of "perception", I really think in my case it's "capability", pure and simple. I've programmed for thousands of hours in both styles, so we're well past the possibility of this being an adaptation problem.

I am totally convinced that the advocates of dynamic programming are right, too, just possibly built differently. For example, if I had an order of magnitude more working memory than I have as an individual (I'm assuming that's neurologically plausible), maybe I'd view dynamic programming differently, too.

I’m a proponent of dynamic typing. I’d say the same thing. I don’t have enough working memory in my head to store the compile-time type information about every relevant variable, in addition to the actually important information about what the runtime data could be.

The way that I write static-typed code is by imagining how I would write dynamic code to solve the problem, and then additionally imagining what types and type constraints I need to add.

I honestly think it’s a kind of an instance of Paul Graham’s Blub Paradox. I know JavaScript and I spent years writing JavaScript. So if you ask me to write TypeScript, well, I write the JavaScript that I want to write and then go back and add types to make the typescript compiler happy.

There are a bunch of other things I could talk about. I should write a post.

> I don’t have enough working memory in my head to store the compile-time type information about every relevant variable

Neither do I, but I know the compiler will check that for me so I don't need to hold all of that in working memory. I know my IDE will always be able to tell me the types too, and flag if anything is wrong immediately.

The different points of view on this are really interesting.

In the end both approaches work well enough to keep companies in business. Companies fail not because of static or dynamic typing but because of marketing, internal fights, etc. The technical details are something that impacts very rarely.

Personally I worked in C for the first years of my career. Then the web happened and the two languages for it were Perl and Java. No more mallocs and frees, it was so great that I kind of forgot C. Then I was assigned to higher level tasks than programming and when I came back to it almost 10 years later I refreshed my Java (I kept doing Perl for my own stuff - CLI scripts and CGIs) and discovered Ruby on Rails. I realized that I could do the same web apps I was writing in Java with much less code and without having to lose my time after obvious but nearly useless details such as specifying that a given variable is a string, or number and how big, or an array of that class of objects indexed by strings (I intentionally use generic terms), etc. It's almost always clear what it is, especially if one picks good names for identifiers. There are some hiccups but not every year.

By the way, a great feature of Elixir is pattern matching in function definitions. In a pythonish pseudocode

  def fib(0): 0
  def fib(1): 1
  def fib(n): fib(n-1) + fib(n-2)
Of course n is an integer. It works with floats too and probably fails with anything else. But who would run fib on some complicated not numerical class that happens to implement the - operator?

I accept the argument that providing type information to a compiler lets it generate faster code. However none of my customers from the last 10 years care about that argument and they selected their technological stacks. Like everybody else they care about getting features done as quickly as possible. They all run their services on a single server, make enough money to pay themselves, their employees and a bunch of consultants like me.

> The way that I write static-typed code is by imagining how I would write dynamic code to solve the problem, and then additionally imagining what types and type constraints I need to add.

Is that not how everyone writes static typed code? You have a need for a variable holding some data, you think about the bounds of that data, you pick a type. What other way would you do it?

The problem with dynamic typing isn't in the first-write. It's all in your head then. It's in the 2 year later bugfix, when you're looking at a function and wondering what kind of data is being passed into it. And then you find all the places that call that function and still can't work out what fields that object will have, or whether they're numbers or strings.

> The problem with dynamic typing isn't in the first-write. It's all in your head then. It's in the 2 year later bugfix

The 2 year later bugfix is often easier I agree. But for me by far the biggest difference is speed and effectiveness in writing new code. I'm not just much faster, but also much better with typed code probably because it fits the way my brain works better.

> Is that not how everyone writes static typed code?

For me the process is a bit opposite. I tend to write the interfaces first, usually until the entire routine of whatever I am writing is complete. So e.g. only the types accepted and returned by functions, but not the actual function itself. Then I go back and add the code itself usually at the very end.

My working memory is garbage and I do prefer working with dynamic langs, however. (I also have ADHD)

I do agree though if I have to work with spaghetti code, I'd much rather work with a language that has a proper type system (I mean a proper one, like OCaml, Standard ML, Rust, Gleam, Etc.) I think static typing in these languages doesn't get in the way, they all have varying degrees of type inference, the type system is sound and uncomplicated. Whereas a Language like Typescript's type system (of Facebook's Flow for JS) had my head spinning, It often felt like playing a mean spirited scavenger hunt with Simon from Simon says.

As far as dynamic langs go, some languages are terrible to work in, (Perl). and other languages because of strong conventions (Ruby and Elixir,) I find very very easy to work in, write tests, create libraries that use DSLs, etc.

So I guess I'm in the middle? leaning in the dynamic langs direction though.

For me personally, my new theory is its an ADD thing. I'm older but recently came to fully appreciate how ADD my mind is, and how I've basically built many habits around coping with it. More recently I learned types is one of those things. I realized with types I can off load a ton of my working memory into the type system. I can bounce between ideas the way my brain wants me to without losing any state, because I'm always setting up the interfaces to the various thoughts I had. And the IDE knows how to take advantage of course, linking everything, popping up docs and hints and etc for every little idea. And so the result is it just matches my brain's natural patterns.

I still remember being quite shocked many years ago when I took a job using Java of all things, I was so fearful coding would take forever. It was my first typed language. But within months, I was faster, by a lot. I would write a lot more code before I had to test it, and once I began testing it there were few if any surprises. Now I'm working in Ruby, and without a debugger and constant tests, I feel I can't hardly get anything complex done in a reasonable amount of time. Like you I thought this was a hurdle that would pass, but while I'm far more effective than when I started, I find that its overall just mentally taxing to write code in this language.

Yet at the same time, when I pair with people who do not dislike Ruby, and watch them work, they are constantly asking "What is this" and "how does this work" and navigating parts of the codebase by grepping. They are effective, and I know its been studied a bit. But to my eyes, they would so obviously be far more effective with types, even when they state they dislike them, I just can't accept its a generally better approach in the absolute sense. I won't judge people for preferring a non-typed language. But I'll likely not accept another job where I can't use a typed language.