Strong vs Weak Typing: Can't we have the best of both worlds?
I've seen lots of arguments on the merits of weak typing. It encourages flexiblity. It lets me write code faster. I don't worry about the details until later. I can do cool runtime tricks.
I don't buy it. I use a strongly typed language because the code it produces is more robust. Typing solves a slew of common programming errors all at once. It ensures that my code will always do exactly what I mean, no more and no less.
And yet... I can see the advantages of weak typing too. Java is a better prototyping language than C++ but it's no where near the speed of Perl for whipping up something quick.
Why do we have strong typing anyway? I can only think of two things. First is performance. If you better specify what you want then the compiler can make faster code. The second is for people. The computer doesn't really care if this string really contains a number. It's all just bits in the end. The typing is for you, the programmer. To help you avoid mistakes. To express what you want the code to do to another programmer. It could be someone using your API, or someone modifying your code, or even yourself hacking on your own code in the future. Typing is a more detailed expression of what you want. But creating that expression can be time consuming and constraining.
But what if we could have the best of both worlds. A language that was both strongly and weakly typed, but at different times. What if I could declare at the top of each module (class, file, or package level?) how much syntatic sugar should be applied.
At it's loosest level you would have:
- no required variable declaration
- foreach, other loop constructs
- dynamic casting
- no required exception handling
- inline regex
- any indentation you want.
At stronger levels (less sugar) you have to declare everything:
- must declare all variables, and at the right location
- only standard looping constructs
- explicit casting
- required exception declaration
- all other syntatic sugar turned off
- Maybe bad indentation and no javadocs would be a compile error too.
Imagine if the forthcoming generics allowed anything to be stuffed in and out of a List in the weak mode and required you to declare the type of List in a stronger mode. Bingo! The ease of Perl with the robustness of Java.
I think such a system would help with three scenarios:
For managing long lived code. We have a pattern of sugar going down as the module stability goes up. Newer code is in flux and tested constantly so it's okay to have the compiler make assumptions. As the code is used more, and more components are dependent on it, we clamp down and explicitly define everything.
It's good for dealing with developers at different skill levels. Developers who's expertise lies in other areas (say graphic designers) do the prototype using sugar mode, not having to worry about the ins and outs of casting and exceptions. Then the real developers refactor it to be more solid if the prototype ends up being used.
You get the benefits of strong typing when you open up old 'hardened' code. Then if you break something you know right away because the compiler is very unforgiving.
The language would scale from prototype stage, through development, and on to deployment and maintenance. As the risk of breakage increases so does the strength of the typing to hold it all together.