C is to Java as Java is to what?
11 years ago I first encountered Java. Before then I mostly used C. I immediately loved how Java kept familiar C constructs but protected me from the most common, most difficult, and most time-consuming bugs. No more string buffer overflows? Awesome! Out-of-bounds array indices caught at runtime? Awesome! No need to allocate and (forget to) release memory? Awesome! No more core dumps? More than awesome! This is what I imagined programmer heaven to be like.
Even expert C programmers often wrote code that had buffer overflows and memory leaks. Making sure code didn’t have such problems took a lot of hard-to-test mental reasoning. Introducing such problems in maintenance code was a continual danger.
I doubted that Java could offer these features while giving reasonable performance. And in fact, in early versions it couldn’t. But over the years all sorts of optimisations have made Java performance adequate for most computing tasks.
Jump forward to today. My most troublesome bugs in Poker Copilot lie in a different area: concurrency mostly in the form of thread-safety. It’s possible to have two or more pieces of code running more-or-less in parallel, accessing the same resources, sharing information, and needing to co-ordinate their activities.
Even expert Java programmers have trouble writing thread-safe code. Making sure multi-threaded code doesn’t have synchronisation problems takes a lot of hard-to-test mental reasoning. Introducing such problems in maintenance code is a continual danger.
I use the Java concurrency API. It’s good. It helps me a lot. I’ve read, re-read, and tried to grok Java Concurrency in Practice. It’s also good and helps me a lot. But these are not enough.
What I long for is a language that’s similar to Java but designed at every level to help write multi-threaded code. Something that offers me familiar constructs and concepts. Yet something that offers me better help for writing thread-safe code. Perhaps a language where objects are immutable by default, unless I specifically mark them as not immutable (Immutable objects make concurrency easier). Perhaps a language where I can mark a class as synchronized, which automatically makes all methods in the class synchronized (therefore ensuring that only one method in the class can run at once). Perhaps a language where parameters are passed as deep copies by default, or as copy-on-write objects, unless I mark them otherwise.
Many Java projects are riddled with obscure concurrency bugs. It’s hard to get even the most basic code right, as I demonstrate with code to format a date as a String.