Via Lamda the Ultimate: Gradual typing as the ultimate unification of static and dynamic typing. The basic idea is that the type system does not enforce you to specify types, but when type information is present, it is used for static checking. This way, you can reinforce the structure of your program by using static types, but you need not be hindered by it when you need more flexibility. The paper's references are worth reading themselves, especially (a two year old, but just now discovered by me) "Static Typing Where Possible, Dynamic Typing When Needed: The End of the Cold War Between Programming Languages" by Erik Meijer and Peter Drayton. I was already quite delighted by the abilities of type inference in Scala as compared to Java, but the possibilities outlined in these papers are such that I just can't wait for them to get adopted by other mainstream programming languages on managed platforms.
I'm all for contracts in programming - the more intentions you can express in the source code in a form that the compiler can understand and enforce, the more errors you have caught early. Static typing is just a subset of possible contracts you can enforce on your code. Also, contracts allow you to write much terser code where eventual ambiguities arising from omitting declarations can be resolved by applying contractual expectations in effect. However, the critical point here is "can" - it gives you the most flexibility when you "can use it" to express the intents but you aren't forced into a "must use it" as you are with lots of today's statically typed languages. To me, an ideal language and compiler would be one that:
- Has broad expressive power for programmer intentions in forms of type declarations and contracts, but
- doesn't force you into using them, however
- enforces them when they're used, and ultimately
- can clearly indicate which pieces of code are compiled as dynamically typed so I can periodically scan the code for unwanted type weakness.
Of all this, it'd already be a big improvement if at least normal type inference got into Java in the foreseeable future, just as it got into newest C#. In the meantime, there's always Scala for more pleasant JVM work. Yes, I know I talk about Scala too much lately.