| > Short-answer is yes, and there's been lots of work done to go even further than having static typing and have formal verification for smart-contracts. Yes, I've looked at some of these projects before. And I certainly think it's a good idea to use automated tools to try to prove properties about programs. But I'm more excited about things like property testing than I am about things like strong type systems. And I'm wondering specifically what is the value they bring. No offense, but all of the answers I've gotten so far are very vague, and don't really address my question. I don't doubt that strong type systems can catch bugs, I am wondering how their capabilities in catching bugs differ from test suites. Let me give you an example, say we have a hypothetical language with a strict type system, and we declare a variable to be of type List[Foo]. Then later we use that variable as if it was really of type Foo. That's not gonna work, and a type-checker would catch that at compile-time. But a test suite (that covers the variable access) is going to catch that as well, because the code won't behave as it should. At which point is a strong type system going to surface a bug that a good test suite would not have? Like, can you give an example? > Not sure what you mean by "reasonable" (is it extensive? testing pathological cases? where do you draw the line?). The line is as variable as the strictness of the type system we would compare it to. I guess one could argue that a type system will force the programmer to satisfy it, while a test suite can be written very sloppily. So maybe there is some kind of signalling value in using these types of languages. |
Well, for one they can prove the absence of certain classes of bugs. Buffer overflows, for example. No amount of testing can do that.
Obviously most languages have "escape hatches" to do inherently 'unsafe' things like calling into C, but then at least you know exactly which bits to audit especially rigorously.
> But a test suite (that covers the variable access) is going to catch that as well, because the code won't behave as it should.
How many different List[X], where X != Foo do you need to test with to have the assurance you need? Are those tests that will actually get written? (IME it's pretty rare to see such "negative" tests, but then I mostly work in typed languages where such tests are usually unnecessary...)
There's also the really huge advantage to types that they actually document a machine-checked contract in a way that integrates seamlessly with the language. There's no such consistency in e.g. JS-land. Now, those contracts may be pretty vague (in e.g. Java or C#), but in Haskell for example they include such things as "does this function have any side effects?". That's extremely powerful, but it's hard to appreciate just how powerful until you have experience in those type systems.
EDIT: Also, don't forget that tests also have costs -- they have to be maintained just like the rest of the program, and static types can drastically cut down on the amount of tests you need to write+maintain.