Break Java!


As some of you might have noticed I am not extremely fond of everything the Java language. I have spent some time lately trying to figure out how I would change the language if I could. These changes are of course breaking, and would never be included in regular Java. I’ve had several names for it, but my current favorite is unJava. You can call it Java .314 or minijava if you want. Anyway, here’s a quick breakdown of what I’d like to see done to make a better language out of Java without straying to far away from the current language:

  • No primitives. No ints, bytes, chars, shorts, floats, booleans, doubles or longs. They are all evil and should not be in the language.
  • No primitive arrays. Javas primitive arrays are not typesafe and are evil. With generics there is no real point in having them, especially since they interact so badly with generic collections. This point would mean that certain primitive collection types can’t be implemented in the language itself. This is a price I’m willing to pay.
  • Scala style generics, with usage-defined contra/co-variance and more flexible type bounds.
  • No anonymous inner classes. There is no need for them with the next points.
  • First class methods.
  • Anonymous methods (these obviously need to be closures).
  • Interfaces that carries optional implementation.
  • No abstract classes – since you don’t need them with the above.
  • Limited type inference, to avoid some typing. Scala or C# style is fine.
  • Annotations for many of the current keywords – accessibility specifically, but also things like transient, volatile and synchronized.
  • No checked exceptions.
  • No angle brackets for generics (they really hurt my eyes. are there XML induced illnesses? XII?). Square brackets look so much better.
  • Explicit separation of nullable from non-nullable values.

These points are probably quite substantial together, but I still don’t think the language would be that difference from Java in syntax and semantics. The usage patterns would be extremely different though. You wouldn’t sacrifice any performance with these kinds of things – they wouldn’t change the characteristics of the output that much, and I believe these things could make the language smaller, cleaner, and easier to work with.



Language design philosophy: more than one way?


When talking about how dynamic scripting languages are designed, people have a tendency to divide them into “There is more than one way to do it” and “There is one way to do it”. Perl is the quintessential example of “more than one way”, and Python is the opposite, going so far as to make it impossible to have your own indentation.

These different ways of doing things really divide programmers. Some hate the way Python gives you a bondage strait jacket and no scissors, while some programmers love that they don’t need to make any choices and that everyone’s code will be equally readable.

From a pure perspective, the Python philosophy seems to be the right one, but it just doesn’t work for me. In the same way, I agree with Perl’s way of doing things, but the problems that cause in most Perl code is just amazing. Sometimes it feels like the Python way is actually directly a result of someone reacting extremely badly to a Perl code base and decided to never allow that to happen in Python.

So what’s the point? Well, the point is Ruby. In fact, Ruby has almost all of the flexibility of Perl to do things in different ways. But at the end of the day, none of the Perl problems tend to show up. Why is this? And why do I feel so comfortable in Ruby’s “There is more than one way to do it” philosophy, while the Perl one scares me?

I think it comes down to language design. The Python approach is impossible for the simple reason that what the language designer chooses is going to be the “one way”, by fiat. Some people will agree, and some will not. But what I’m seeing in Ruby is that the many ways have been transformed into idioms and guidelines. There are no hard rules, but the community have evolutionary evolved idioms that work and found out many of the ways that doesn’t work. This seems to be the right way – if you do the choice as a language designer, you have actually chosen the people that will use your language: that’s going to be the persons who doesn’t dislike the language designers choices. But if you leave it open enough for evolutionary community design to happen you can actually get the best of both world: both a best way to do things, and something that works for a much larger percentage of the programmer world.

I have come to believe that this is one of the major reasons that Ruby feels so good to me, and is such a good language. And it’s a lesson for language designers. When you choose philosophy, make sure to take the possibility of communities and idiom evolution into account.



Soft and hard layers


I hadn’t read this specific c2 post, but it’s funny how much of what I write is just a rehash of stuff Cunningham and company came up with 15 years ago. Well. I guess that’s why they’re the masters and I’m not.

Incidentally, this is my 300th blog post, since starting this blog a little bit more than 2 years ago. Time rushes by, don’t it?



Viability of Java and the stable layer


This post is basically a follow up to Language explorations. That post had several statements about what I believe, and some of them have been a bit misunderstood, so I’ll try to substantiate them a bit more here. Specifically, I want to talk about the viability of the Java language and whether “the stable layer” should be a static or dynamic language.

Lets begin with the stable layer. First, notice that I didn’t have any specific definitions for the different layers when I wrote the post. In fact, I think that they are inherently a bit fuzzy. That’s OK. DSL’s are also quite fuzzy. The attributes I put at the stable layer is first of all that it shouldn’t need to change much. In a smaller application, you can actually look at supporting structures as the stable layer, things like application servers or web servers. But for larger applications I find that you usually need your own stable kernel.

The reasons I choose static typing for stable layer is for several reasons. Performance is absolutely one of these, since everything will run on this base it’s an advantage if that part is as performant as possible. Secondly, I am no dynamic language, TDD purist that says that static typing is totally unnecessary. Static type checking can be very helpful, but it stops you from having a malleable language. So the kernel should be stable, this means that as much checking as possible is necessary. None of these requirements explicitly preclude a dynamic language, but the specific features of dynamic languages doesn’t really come to their rights at this level, and also leading to performance and static type checking suffering.

The more contentious part about my post seems to have been my off hand comment that I don’t believe Java is really good for anything. I didn’t give much reason in that post, and people have reacted in different ways, from saying that “Java is really good” to “Why are you involved in JRuby if you think Java is so bad?”. So lets start with why Java is a bad language. (I am only talking about the language here, not the platform). Also, that Java is a bad doesn’t say anything about the worse alternatives, so no comments along the lines of “if you think Java is so bad, why don’t you use X instead”.

In short:

  • Java is extremely verbose. This is really a few different problems in one:
    • No type inference
    • Verbose generic type signatures
    • Anonymous class implementations
  • There is no way to create new kinds of abstractions:
    • No closures
    • Anonymous classes are a really clunky way to handle “block” functionality
  • Broken generics implementation
  • Language is becoming bloated

A few notes. That Java is becoming bloated is one of those things that people have been blogging about lately. After 1.5 came out, the complexity of the language got very much larger, without actually adding much punch for it. The improvements of generics were mostly negated by the verbosity of them. Fixing all the problems above will bloat the language even more. And at the same time, programming in Java is needlessly painful right now.

So, lets look at the question about why I’m working on JRuby. Well, first, I believe the JVM is a very good place to be at. It’s the best platform out there, in my opinion. The libraries are great, the runtime is awesome, and it’s available basically everywhere. The bytecodes of the JVM spec is good enough for most purposes. There is some tweaking that can be done (which we are looking at in JSR292), but mostly it’s a very nice place. And working on JRuby is really one of the ways I’ve seen how bad Java as a language is. We are employing several different tricks to get away from the worst parts of it, though. Code generation is used in several places. We are generating byte codes at runtime. We are using annotations to centralize handling of JRuby methods. And we are moving parts of the implementation to Ruby. I believe that JRuby is important because it can run in the same environment as Java, but without the problems of Java.

What are the solutions to the problem with Java? There are basically two different ways. Either define a subset of Java, not necessarily totally compatible, that takes the best parts of Java syntax, does away with the problems and so on. That should be possible, but I don’t know anyone who has done it. Or, you can go with an existing static language on the JVM. Here you have two choices – either one of the ports of existing extremely static languages (like ML or Haskell), or you can go with something like Scala. I haven’t decided on the best solution here yet. The only thing I’m sure of is that Java in itself is a problem. I’m investigating Scala, but maybe Scala isn’t the right answer either. We’ll see.



Keywords in languages


It’s nice to see how the amount of people looking into Scala has really exploded lately, based on the rush of blog posts an discussion.

One of the things I find a bit annoying about Scala is the proliferation of keywords. Actually, this is something I really don’t like in any languages. A language should be as keywordless as possible. Of course, such a vision goes against ease of implementation for language implementers, so there always needs to be a balance here. Coming from languages such as Lisp and Io, it’s amazing how clear a language can be with a well chosen message passing or invocation model. In fact, both of those languages have zero keywords. That makes it incredibly nice to implement whatever you want.

Actually, Java has been quite good at not taking much more keywords than they had from the beginning, so I found it a bit annoying when I tried to build a fluent interface in Scala, and found out that the word “with” is a keyword. And it’s a keyword in the strictest sense, meaning you can’t use it in places where you can’t use the “with” keyword anyway. So there is no way to implement a method named “with” in Scala. Annoying. It’s just, the English connection words are so much more useful for method names, especially when you can use the methods in “operator” position. Then you just want to be able to use all these words.

So. If you design a language, make sure that you take care to actually add every keyword extremely carefully. If you can, make sure that keywords can actually be used for some things when there is no ambiguity. Of course, I’m not proposing the kind of madness you can do in some languages, where a statement such as “IF IF THEN THEN” is valid, since the first IF is a keyword, the next is a variable name, etc. But be reasonable about keywords. They are sometimes necessary, but not always as often as people believe.