I think we have a major philosophical difference and talking a bit past each other.
Here are the two things why I am using Scala:
1. Confidence
Scala gives me the confidence that I can build software the way I imagine, I can focus on the user of my code, not on making the compiler happy.
While there are plenty of languages which make easy and medium problems nice to solve (Clojure and Erlang certainly belong to this group), Scala is one of the few languages which keeps supporting me regardless of whether my problem is easy, medium or incredibly hard.
In my experience, the work on making hard problems easier had a huge tricke-down effect which in turn improved Scala's issue solving capabilities for simple and medium issues.
I think the language is better for that and certainly ahead of Erlang and Clojure here.
While most hard problems are not common, they are often fundamental. Not being able to solve some issue in the best possible way can have huge negative impact on the whole application and library design.
That's why for instance making it easier to create macros wasn't the first problem to concentrate on. Instead, developers made sure that users of macros had the best possible experience and focused on having one, unified API for reflection, the macros and the compiler, hugely simplifying semantics while re-using battle-proven code.
Macros makes it possible to pull more functionality out of the language and out of the compiler; into libraries. For instance C# 5 introduced huge language changes with adding async/await to the language. In Scala no language change is necessary: Adding support for async/await would be just a library.
Unlike Macros in most other languages and inferior approaches like in Java, Scala macros are type-checked as regular Scala code at the definition site as well as the macro expansion at the call site, removing huge amounts of tricky issues all at once.
Great care is taken to make and keep Scala a highly regular language with only the minimal amount of hardcoding necessary to make things work. Unlike Clojure, it doesn't have special-cased syntax for collections and a few “blessed collection types” shipping with the language. Unlike Erlang, Actors are not built into the language.
In both cases, Scala avoids irregularity by enabling users to build libraries which can be improved and be replaced without much trouble.
Yet Scala seems to want to address every problem with
a language feature, and in this case it's a huge one.
This for instance is something I would call blatantly wrong. You confuse the distinction between a language like C# or C++ which adds tons of features to address every fashionable problem and Scala, which keeps its feature count low and orthogonal but manages to solve a lot of those problems by just being a better designed, more expressive language.
On the other hand, when I look at Erlang and Clojure
(or Ruby, though I'm less familiar with it), I see
languages that were designed by people who sat down
and thought long and hard about which are the top one,
two or three most burning problems of software
development, and then tackled those and only those.
Well, that's nice, but I think it is even better that some people decided to bite the bullet and improve a lot of things instead of just building yet-another-language which improves on parts which the creator found subjectively important and regresses on dozens of others.
Is it hard to build a language with these intentions? Sure! Is that a reason not to do it? Absolutely not.
I think one part where Scala has basically proven tons of people wrong is OO/FP. People have been saying for decades that OO and FP are fundamentally opposed to each other. Scala just went ahead and proved them wrong, showing that just because some earlier approaches like OCaml or F# are not that good doesn't mean it is impossible.
Also, people have been claiming that there will always be a impedance mismatch between languages and databases. Scala went ahead and showed that it has not to be that case.
I want the best OO functionality combined with the best FP functionality.
I want to be able to use higher-order abstractions combined with the best performance and efficiency.
I want libraries written in the best possible way, not in the way the language decided it was convenient.
I want to use the right tools for the right job without having to migrate from one language to another.
He may be wrong, and he may be right, but he made a decision.
It's 2013. Let's stop forcing people to make pointless decisions. I just won't choose between things if I can have both, combined into a consistent library.
Clojure or Erlang just don't deliver here and that Clojure is the best language to manage state is highly debatable, too.
I think you should rarely use this tool or that, so I'm
leaving them out of the toolbox. When you need them, buy
them separately
This is by the way exactly what Scala says. The language ships with the tools to enable people to build libraries. By default, everything is left out.
Don't take me wrong, a language should be as easy as possible — but not easier.
2. Community
It is pretty non-sensical to ask “What is the one or two things Scala is better at than any other language?”. There plenty of things it does better, because “good enough” is just not good enough for people in the Scala community.
In general the Scala community is highly critical of every aspect and tend to push things to the current state of the art or beyond it if they feel something can be solved in a better way. This has led to a huge increase of consistency and quality throughout the ecosystem, so that having a few good parts and a lot of mediocre parts is just not acceptable to most Scala developers anymore. They demand the best tools one can possibly build.
Anyway, I think your use of “coherent” is getting more clear, but imho makes less and less sense. You are basically asking for a silver bullet and are unhappy that Scala tells you that for many problems, there isn't one. I think this is one of the core advantages of the community: It doesn't try to sell you some “ultimate solution”, avoids ideological bullshit and treats people as grown-ups.
For instance, Scala's Akka team (those who work on concurrency-related libraries) had an interesting talk recently where the demonstrated something like 9 different approaches/techniques to tackling concurrency, all of them with different benefits and drawbacks, with the main conclusion of “pick your poison”.
I think this is one of the core distinctions between Scala's diverse community and other, more anglo-saxon-centric communities: People who have grown up in the US just love to swallow shallow marketing non-sense and respond extremely well to claims about “one true way” or “silver bullets”.
If somebody came with that approach to the Scala world, people would tell him/her that he/she is either lacking experience, has poor judgement, or probably both and show him/her why he/she is wrong.
The way people carefully evaluate different approaches and document its pros and cons instead of following the next hype is exactly why I'm using Scala.
Scala's strength is shipping efficient, reliable and fault-tolerant software at a rapid pace.
Well, best of luck with Scala, then. I am aware that there are people out there who like Scala, some of them even like it for the reasons you mention, and some of those even seem to find it elegant (BTW, I watched a talk[1] by Marting Odersky in which he tries to explain why he thinks all those Scala features should be crammed into a single language; even he didn't seem half as convinced as you are :)). It's good to have choices in the JVM ecosystem.
I'm curious what you find it is about Scala that lets you solve hard problems that you don't find in Clojure. Is it static typing and/or OO support? I'm also curious what you don't like about having syntax literals for vectors/maps/sets?
For instance Scala's support for composition and modularization of library fragments which allows you to separate even heavily interwoven concerns into tidy parts and put them together whenever and wherever you like it (or exchange some parts of it completely)
Static typing is certainly a factor, too. Scala allows me to not only design APIs which make it hard to be abused or misused, it makes it possible to encode many things I care about into types so that “wrong” code won't even compile.
With macros, there is now a whole new breed of libraries which add support for types to tasks which were to get wrong before, for instance
- the whole type provider business where one points to soma data source (like a database) and tells the compiler to figure out the right types on it own
- compile-time checked and SQL-injection-safe string interpolation like sql"""SELECT * FROM PERSONS WHERE $predicate"""
- sqlτyped (github.com/jonifreeman/sqltyped) which can compute types from SQL strings
- macros which transpile Scala code to JavaScript, inline (jscala.org)
- macros which can synthesize typeclass instances on-the-fly, like used in Scala's new serialization library (speakerdeck.com/heathermiller/on-pickles-and-spores-improving-support-for-distributed-programming-in-scala)
- Scala's async library (github.com/scala/async)
Regarding collection literals ... it certainly isn't that important in languages like Clojure where performance is not of great importance, because everyone just picks the one which come with the language and hopes it won't be too bad. Implementing new collection types is just not common here (like in many other untyped languages like PHP, Ruby, Python, JavaScript, etc.).
In Scala, blessing a few chosen collection types with special rules and syntax just won't fly. Developers demand first-class support for all collection types including the ones they define themselves.
Reserving some special rights which no one except the language creators are able to use just gives them an unfair advantage. All implementations should compete on the same ground so that the best one can win, and not the one which benefits from special-cased, hard-coded syntax rules.
Here are the two things why I am using Scala:
1. Confidence
Scala gives me the confidence that I can build software the way I imagine, I can focus on the user of my code, not on making the compiler happy.
While there are plenty of languages which make easy and medium problems nice to solve (Clojure and Erlang certainly belong to this group), Scala is one of the few languages which keeps supporting me regardless of whether my problem is easy, medium or incredibly hard.
In my experience, the work on making hard problems easier had a huge tricke-down effect which in turn improved Scala's issue solving capabilities for simple and medium issues.
I think the language is better for that and certainly ahead of Erlang and Clojure here.
While most hard problems are not common, they are often fundamental. Not being able to solve some issue in the best possible way can have huge negative impact on the whole application and library design. That's why for instance making it easier to create macros wasn't the first problem to concentrate on. Instead, developers made sure that users of macros had the best possible experience and focused on having one, unified API for reflection, the macros and the compiler, hugely simplifying semantics while re-using battle-proven code. Macros makes it possible to pull more functionality out of the language and out of the compiler; into libraries. For instance C# 5 introduced huge language changes with adding async/await to the language. In Scala no language change is necessary: Adding support for async/await would be just a library.
Unlike Macros in most other languages and inferior approaches like in Java, Scala macros are type-checked as regular Scala code at the definition site as well as the macro expansion at the call site, removing huge amounts of tricky issues all at once.
Great care is taken to make and keep Scala a highly regular language with only the minimal amount of hardcoding necessary to make things work. Unlike Clojure, it doesn't have special-cased syntax for collections and a few “blessed collection types” shipping with the language. Unlike Erlang, Actors are not built into the language.
In both cases, Scala avoids irregularity by enabling users to build libraries which can be improved and be replaced without much trouble.
This for instance is something I would call blatantly wrong. You confuse the distinction between a language like C# or C++ which adds tons of features to address every fashionable problem and Scala, which keeps its feature count low and orthogonal but manages to solve a lot of those problems by just being a better designed, more expressive language. Well, that's nice, but I think it is even better that some people decided to bite the bullet and improve a lot of things instead of just building yet-another-language which improves on parts which the creator found subjectively important and regresses on dozens of others.Is it hard to build a language with these intentions? Sure! Is that a reason not to do it? Absolutely not. I think one part where Scala has basically proven tons of people wrong is OO/FP. People have been saying for decades that OO and FP are fundamentally opposed to each other. Scala just went ahead and proved them wrong, showing that just because some earlier approaches like OCaml or F# are not that good doesn't mean it is impossible. Also, people have been claiming that there will always be a impedance mismatch between languages and databases. Scala went ahead and showed that it has not to be that case.
I want the best OO functionality combined with the best FP functionality. I want to be able to use higher-order abstractions combined with the best performance and efficiency. I want libraries written in the best possible way, not in the way the language decided it was convenient. I want to use the right tools for the right job without having to migrate from one language to another.
It's 2013. Let's stop forcing people to make pointless decisions. I just won't choose between things if I can have both, combined into a consistent library.Clojure or Erlang just don't deliver here and that Clojure is the best language to manage state is highly debatable, too.
This is by the way exactly what Scala says. The language ships with the tools to enable people to build libraries. By default, everything is left out.Don't take me wrong, a language should be as easy as possible — but not easier.
2. Community
It is pretty non-sensical to ask “What is the one or two things Scala is better at than any other language?”. There plenty of things it does better, because “good enough” is just not good enough for people in the Scala community.
In general the Scala community is highly critical of every aspect and tend to push things to the current state of the art or beyond it if they feel something can be solved in a better way. This has led to a huge increase of consistency and quality throughout the ecosystem, so that having a few good parts and a lot of mediocre parts is just not acceptable to most Scala developers anymore. They demand the best tools one can possibly build.
Anyway, I think your use of “coherent” is getting more clear, but imho makes less and less sense. You are basically asking for a silver bullet and are unhappy that Scala tells you that for many problems, there isn't one. I think this is one of the core advantages of the community: It doesn't try to sell you some “ultimate solution”, avoids ideological bullshit and treats people as grown-ups.
For instance, Scala's Akka team (those who work on concurrency-related libraries) had an interesting talk recently where the demonstrated something like 9 different approaches/techniques to tackling concurrency, all of them with different benefits and drawbacks, with the main conclusion of “pick your poison”.
I think this is one of the core distinctions between Scala's diverse community and other, more anglo-saxon-centric communities: People who have grown up in the US just love to swallow shallow marketing non-sense and respond extremely well to claims about “one true way” or “silver bullets”.
If somebody came with that approach to the Scala world, people would tell him/her that he/she is either lacking experience, has poor judgement, or probably both and show him/her why he/she is wrong.
The way people carefully evaluate different approaches and document its pros and cons instead of following the next hype is exactly why I'm using Scala.
Scala's strength is shipping efficient, reliable and fault-tolerant software at a rapid pace.