Hacker News new | past | comments | ask | show | jobs | submit login
A better Java: Scala or Xtend? (mac-vicar.com)
24 points by dmacvicar on Sept 30, 2012 | hide | past | favorite | 32 comments

I think it depends a lot on what you're wanting out of the language.

If your primary goal is Java sans pain, then Xtend, Kotlin, or perhaps Groovy should fit reasonably well and have a gentle-ish learning curve. Both Xtend and Kotlin seem to be designed particularly for this niche, with a dash of Scala-is-too-complex mixed in to their marketing materials.

If you're wanting an interesting new language that goes beyond traditional Java thought patterns, however, Scala (or Clojure) seems like a much better option. Both Scala's type system and its deep and insightful fusion of OO and functional thought make it a far more interesting language to think about and work with.

IMO, YMMV, etc. of course.

Scala to me feels like the C++ of Java. There's a billion language features and each time I try to learn a new one, I run into gotchas and inconveniences. I'm not convinced an average or even above-average programmer can keep all that stuff straight in his head, cognitive energy that's better spent on actual programming.

For instance, what the heck is the method

GenTraversableLike.++[B >: A, That](that: GenTraversableOnce[B])(implicit bf: CanBuildFrom[List[A], B, That]): That

? That is all one method definition. Famous Java-isms like Enum<E Extend Enum<E>> are tame in comparison.

Things like this are the #1 reason I haven't embraced Scala, despite this constant itch I have to learn strongly typed functional programming. And who knows if they might capriciously change Scala tomorrow, like the time they decide to break binary compatibility of type signatures in compiled Scala classes, after which I spent an hour trying to figure out why the heck my IDE was reporting type errors everywhere.

The method ++ adds one collection to another. The specific type signature you are looking at is for the most general possible parallel collection. Obviously in that case the type signature will be complex - it needs to enable the compiler to determine the type of (Set(Superclass()).par ++ List(Subclass(), Subclass2())).

In practice, type signatures written in application code rarely look like that.

Don't get me wrong - Scala is complex. If you don't need the JVM, Haskell is far simpler and cleaner. But you are exaggerating the complexity of it.

>Haskell is far simpler

I disagree. If anything, both Scala and Haskell are comparable to C++ in terms of complexity. Haskell is in fact, a bottomless pit.

During your descent into madness, you may encounter functors, monads, comonads, free monads, higher ranked types, arrows, zippers, existentially/universally quantified types, GADTs, kinds, and the other 300 extra compiler extensions that people use on a daily basis.

Documentation is provided in the form of academic research papers.

Not that I'm saying it's not an exciting journey, but it is a long journey.

At it's core, Haskell is very simple. Functions are always curried. There is no subtyping. Typeclasses are the only method of polymorphism.

Everything you mentioned above is just a library on top of this.

In contrast, Scala has java-style subtyping built into the language, along with traits which are a weird mishmash of typeclasses and interfaces. There is quite a bit of complexity surrounding functions/methods. You have implicits to think about. Heck, just look at the type signatures in both languages and compare.

C++'s complexity stems from the fact that it's one big leaky abstraction on top of C with a ton of warts, not because it derives from complex academic or conceptual depth.

I'm not saying Haskell is easy. I'm just saying they are categorically different kinds of complexity.

Yes, not all complexities are created equal.

Haskell, and to a bit of a lesser extent Scala, have a lot of their complexity arise from combinatorial explosion of interactions of simple features.

Also, relentless abstraction (particularly in Haskell). Yes, you can think of lots of things as arrows. But does it necessarily make it easier to write a particular problem to do so, or does the cognitive load required to maintain the abstraction <-> problem mapping outweigh the benefit of casting it as the abstraction?

I've also found my Scala experience to feel disturbingly reminiscent of C++ (and I have grown to love Scala). I find a significant difference, though, in that C++ has a lot of complexity, while Scala has a lot of complex emergent behavior from a few simple core ideas (and the complexities needed to work out their details).

Then there's the library, where yes, you see a hairy mess like that. Very difficult to read and understand, but it is a powerful combination of relatively simple and orthogonal concepts. Which doesn't necessarily mitigate the complexity.

FWIW, you rarely need to write code with types that complex, and there is talk in the Scala community of how to simplify the presentation of methods with complex types in the documentation. But that doesn't make it more approachable today.

I understand your reaction, as I have felt similar feelings myself.

Would you feel the same way if we applied the situation to English instead of programming languages?

I rather like knowing that there are people who can express thoughts in English that are above my immediate comprehension, and would be loathe to replace English with some other language that prevented them from so doing.

It would feel like Harrison Bergeron applied to programming languages.


I'd like to use any of the alternative JVM languages out there.. However, as someone who already has a great deal of code in JARs, it seems like it would increase complexity for little benefit.

What I am saying is that I don't like the costs of investing into a whole another ecosystem (say Scala or Clojure), with an unproven future, and a smaller market (compared to pure Java). Of course, you can call any JAR from Scala and Clojure, but it seems to me that a Scala/Clojure JARs are not equally callable from Java (or other JVM languages). You start getting into runtime JARs and the basic "impedance-mismatch" of different language abstractions. (For example, for languages with traits, what do those correspond to in Java -- interfaces, abstract classes?)

Ideally, I would like to have a language that can compile a Java class that seamlessly interacts with other Java stuff. The problem is that it seems to me you don't get any of the benefits of Scala, Clojure, in that setup, because the runtime adds a lot of value. Most that you could get are nice syntax for lambdas (which are a bit verbose in Java, but not really a problem for me), but those are anyways coming in JDK 8.

Have people on HN thought about this? People who use alt JVM languages, I am curious about your opinions. Honest question, I am not interested in language flamewars.

Clojure has a fully optional, very grokkable and well-defined map from Clojure to Java, in the form of protocols and gen-class. Protocols are a natural part of the language, and if you need a concrete gen-class, because Clojure is functional it's easy to plug whatever Clojure functionality into a Java interface.

I think this is the main advantage of Xtend. Xtend compiles to plain Java classes and uses the same typesystem as Java. This way you get excellent Java interoperability, as Xtend classes can be used seamlessly from Java and vice versa. This goes so far that I usually mix in my projects Java and Xtend code. I recently wrote a blog post about this topic, as well [1].

[1] http://sebastianbenz.de/5-Things-that-make-Xtend-a-great-Lan...

In my experience Clojure is very callable from Java. For example, Lists and Maps can be passed as normal arguments to clojure functions without conversion step. This works because Clojure favors abstractions over concretions. For example, instead of a concrete cons cells datastructure, Clojure has the ISeq interface. As far as I can tell, calling clojure from Java introduces no overhead at all.

Datomic is a commercial database system developed in Clojure. The peer library is what you use in your client application to query the Datomic server. The peer library is written in Clojure. I expect that means calling Clojure from Java, and including the Clojure runtime jar in a client application, is safe/stable/supported enough to build a business on top of it.

I'm still learning though, so take what I said with a grain of salt.

As others mentioned, Clojure makes it fairly simple to generate a normal Java class containing your Clojure code. In addition, you can access clojure.lang.RT to run your Clojure function directly, like this: RT.loadResourceScript("pkg1/pkg2/runner.clj"); RT.var("pkg1.pkg2.runner", "run").invoke(args);

However, in my experience, Groovy is about as simple as it can be. Just put your Groovy code inside a class and it looks exactly like any other Java class.

There's no Scala runtime. I think you're either mistaken or using the wrong term. Do you mean the standard library? If so then what's the problem with adding that to your classpath?

I get that some of the Scala constructs (e.g. traits) may be unweildy to use from Java, but I think you're unlikely to have a large and growing surface area for that. On a case-by-case basis I think you could just provide a Java friendly interface from your Scala code.

> Ideally, I would like to have a language that can compile a Java class that seamlessly interacts with other Java stuff.

Groovy fits the bill.

Groovy has a lot of interop issues. The dynamic resolution of overloaded methods being just one example. Xtend is much more interoperable as it binds at compile-time just like Java does and uses the exact same type system.

> The dynamic resolution of overloaded methods being just one example.

That has never caused an interoperability issue for me. If there is concern about which method would get picked then use explicit types.

> Xtend is much more interoperable as it binds at compile-time just like Java does and uses the exact same type system

You can enable this in groovy 2 using explicit types and @CompileStatic.

I am a polyglot programmer even though I try to concentrate on languages that I need to get stuff done. I am really enjoying Martin's Scala class https://www.coursera.org/course/progfun, I use Clojure a lot on customer and my own projects, and (J)Ruby is so often my go-to language. And, I use Java a lot, but less than these other JVM languages.

That said, I was having a quiet think while walking in the wilderness recently (I live in the mountains) and I asked myself the tough question: would I have accomplished more in my professional life in the last ten years if I simply always used Java? I honestly don't know the answer but I suspect that the answer is that in some absolute metric of both money earned and productive work for society, just sticking with Java would have been the better call. In the past I have had the same quiet think about just using (J)Ruby.

The big win of being a polyglot programmer is reshaping one's mind to think about problems in different ways, and I don't know if it is worth it.

Scala, Clojure, Kotlin, Ceylon, Groovy and now Xtend. Going to be interesting to see what languages win out in what niches on the JVM.

Just to add more to that list, there is also Fantom (my choice of a better Java) and haXe which also deserves a mention, for managing to hit five or six different platforms.

Well, recently i started learning clojure, and i am surprised by the size of the community and ecosystem ... its big ... and active

i wanted to learn either scala or clojure and decide to pick the language with tighter java libraries integration (the language that makes it easier to use java lib), and according the the reviews i read, clojure won in that area

if the level of activity around clojure continues at this rate, i believe it will easily outshine the competition

also dont discount jRuby, it has a nice following

People on clojure forum were not very nice. I am learning scala with https://class.coursera.org/progfun-2012-001/class/index. Scala guys are very nice and the language is really awesome.

Nothing against Clojure, but I'm curious what you read that made you think Clojure has better Java interop than Scala?

Using Java code from Scala is literally the same as using Scala code from Scala. Same thing if you replace Java with Scala and Scala with Java (with the exception of some Scala constructs that aren't present in Java).

This is not true of Clojure..

a bit late but this is the link where i read it


looked trust worthy to me!

Which ever has the best IDE support.

Approximately nobody codes in Java, rather we code in Eclipse, Netbeans or other Java. It is great because we can still ship the Java code as it is still Java, so I kinda miss things like lambdas and closures, but most of the pain is gone and a lot of things that are still difficult in other languages, such as finding a specific method or class are really easy.

But if you aren't used to program this way, it can take some adjustment.

Java + lambdas

meh, not sure what the "pain" is if you code like a god on eclipse. scala or xtend is java for pussies.

Every line you don't have to write is a line which can't contain bugs. Lack of semicolons makes for better readability. Pre-included functions like map() enable programmers to use best practices, allowing for even terser code. You might have noticed that as a programmer you spend about 80% of your time reading code (if you are lucky, it's your own), so let's not pretend there is no merit to code readability and shortness.

"terser code" is not an end in itself. It is neither a sign nor a goal of well written programs.

No, but all else being equal, code which is shorter and clearer is better than code which is longer. The latter is far more likely to contain bugs. It's the difference between composing a map/filter/reduce pipeline and writing every single loop out by hand.


Applications are open for YC Winter 2024

Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact