5 ms·
I think most people would agree that these two circles overlap on a Venn diagram: ( Bugs found by unit tests ( ) Bugs found by type-checking ) T
by AngryParsley 14y ago
I think most people would agree that these two circles overlap on a Venn diagram:
( Bugs found by unit tests ( ) Bugs found by type-checking )
The disagreement is how much. Also, type-checking is free[1], while unit tests have to be manually written.
I'm glad someone spent a lot of time trying to answer this question, but I don't think it will affect my choice of language in any new project. I like to write code in the languages I like, and bugs be damned.
1. A common argument is that static-typed languages slow development. I'm not touching that land-mine.
- swannodette 14y agoVia Philip Wadler, http://wadler.blogspot.com/2011/09/experiment-about-static-and-dynamic.html http://wadler.blogspot.com/2011/09/experiment-about-static-a...
- akkartik 14y agoOn HN: http://news.ycombinator.com/item?id=4082775 http://news.ycombinator.com/item?id=4082775
- Goladus 14y ago> 1. A common argument is that static-typed languages slow development. I'm not touching that land-mine. If you claim type-checking is free, the counter-argument is not that it "slows development." The counter is that type-checking is not free because it incurs measurable costs. You may sacrifice dynamic features, you may have to add declarations and type casts-- these are all costs whether they "slow development" or not. (Simple solution: don't waste time trying to claim type-checking is free and just focus on the benefits.)
- AngryParsley 14y agoI would feel bad editing my comment now that you've replied, but my original intent was to say that type-checking is "free." At some point the quotes were lost. To get as close to the land-mine as I am willing: I like C. I like Python. I like Ruby. But most of all, I like using the right tool for the job.
- Peaker 14y agoI am not claiming static typing is free. But it is also untrue that you have to "add declarations and type casts". With type inference, you don't actually have to.
- Goladus 14y agoBut you have to use a language with type inference. That's still a cost. Maybe not a big one, but that was my point (and I'm definitely nitpicking a bit, I realize that.)
- dllthomas 14y agoA constraint is only possibly a cost - if it forces behavior you wouldn't have chosen otherwise.
- Goladus 14y agoTrue, but free usually means freedom from both cost and restraint, so the point doesn't change much. I should have said "constraint" rather than "cost". Though the original commenter did follow-up, clarifying that the common interpretation of "free" doesn't closely match the point he'd intended to make
- dllthomas 14y agoFair.
- kingkilr 14y agoa) If you aren't touching that land mine you're missing the point. You can't say that one is free (except maybe it has a cost), and the other has a cost. That's just nonsensical. b) Second, I'm going to argue that tests are actually free. And I think this because I don't care how good static type proponents think they are, I know they don't wait until it compiles and SHIP SHIP SHIP, they actually run their damned program. The alternative to automated testing is manual testing, not no testing.
- wtetzner 14y ago> I'm going to argue that tests are actually free. > The alternative to automated testing is manual testing, not no testing. Actually, unit tests have different costs than manual testing. That doesn't make them free. For example, with unit tests, you now have more (possibly buggy) code to maintain.
- dllthomas 14y ago> For example, with unit tests, you now have more (possibly buggy) code to maintain. Well, that's no problem. Just hit them with a bunch of unit tests...
- cyrus_ 14y agoMany of the unit tests would have to be written in a simply-typed language like Haskell too -- the author notes that only a handful of tests could be entirely eliminated due by the rewrite. Probably worth further study.
- jerf 14y agoIn my admittedly-limited personal experience doing something similar, it's really hard to characterize this in a sane way. What you end up with is a pile of unit tests which are "really testing something", yet, some non-trivial percentage of the tests are still redundant to the type system. You feel like you can't throw it away because of the percentage that is a real test of functionality, but if you'd been starting from scratch with the stronger type system you'd have written fewer tests with very different focus. It's hard to even come up with an example, but consider testing that an HTML generation library doesn't unexpectedly emit text unescaped. The pile of tests you write if you're in Python or Perl mostly translate to Haskell unscathed, in that each individual test still is testing something ("is the href attribute on <a> encoded properly? is the name attribute on <a> encoded properly? ..."), yet considered as a whole the tests have significant redundancy with the type system, because if you set the types up correctly there's a great deal fewer possible ways to screw up than there used to be.
- fhars 14y agoUsing the type system to prevent the generation of malformed HTML (and most types of invalid HTML) at compile time is actually a standard example for a situation where unit tests become mostly superfluous in the presence of a static type system. Some unit tests for the escaping functions in the library can be useful, but code that uses the library can just trust the compiler.
- jerf 14y agoThat's probably why it came to mind. The real instance I encountered wasn't that, but requires so much other context to explain it wasn't a good HN comment. Also, rereading my comment, something that may not be clear, when I said "some non-trivial percentage of the tests are still redundant to the type system", I mean per test. On each test, some non-trivial percentage is actually redundant, not that there is some percentage of tests that are totally redundant. You just remove those, of course.
- x1 14y agoAre we really talking about type checking or the larger circle of validation (of which type checking is just a small part)? ( Bugs found by unit tests ( ) Bugs found by input validation ) Or in other words... String s = "lastname'; drop table user--"; ...is still a perfectly acceptable string. It seems to me that type checking is the simplest form of validation (are you an int, are you a String) and nothing more. It wont tell you if that int is positive or negative or if that string is an email. When dealing with either static/dynamic languages I think more unit tests should be spent validating.
- papsosouid 14y agoNo, this is just common ignorance of static typing. That string is a perfectly acceptable String. But it isn't a perfectly acceptable Query, and you can't pass a String to the database, only a Query. In order to turn a String into a Query, it has to be passed to a function that escapes problem characters safely. You need to use such a function regardless of dynamic vs static typing, but static typing enforces that you always use that function, and can't forget and accidently submit an unescaped string to the database.
- x1 14y ago> but static typing enforces that you always use that function, and can't forget and accidently submit an unescaped string to the database. So you're saying it is impossible to do this without static typing?
- gaius 14y agoTo have the compiler trap accidents for you? How would you do this if a query and a string were the same thing?
- hotlikearobot 14y agoHe is making the point that you can create a separation between Query and string just as easily in a dynamic language; it just gets caught at runtime (preferably during testing) rather than compile time.
- zmoazeni 14y agoContext: My day job has been coding Ruby for years, and I'm a big fan of Haskell. Someone was asking me about my thoughts on static vs dynamic. And I realized that I have two reasons for my tests a) I didn't do something stupid like mistype a method or variable name and b) validate my logic. Sometimes I think it swings 20/80 and others 80/20. But either way, I know that's why I gravitate towards integration tests in Ruby, and that some of them would go away if it were statically typed. Even after coding in Ruby all these years, I'm still just as afraid of (and susceptible to) problems in a).
- mikeryan 14y agoAlso, type-checking is free[1], while unit tests have to be manually written. The use of type-checking doesn't negate the need for unit tests. It just adds another layer of validation. The Unit Test "cost" is still there.
- Peaker 14y agoYou can write far fewer tests if you have good static validation. For example, taken to the extreme, you can write 0 tests in Agda, and still have more assurances about correctness than if you had 100% coverage in a dynamically typed program.