
Why Clojure will win - joshuacc
http://michaelochurch.wordpress.com/2013/08/07/why-clojure-will-win/
======
qammm
I like Clojure but I currently don't see any enterprise adoption of it. I see
some startups and some students and hobbyists using it. Interestingly Scala
seems to get some traction in enterprises here in Germany. I think enterprises
love a lot of language features, complexity, security. Maybe Scala with its
everything and the kitchen sink feature set, static type system, Java-like
syntax and last but not least OOP appeals more to the "manager-friendly
conservatism" as the blog author says.

~~~
happy_dino
While I can't speak of traction in enterprises in Germany, I wonder what the
notion of "Scala with its everything and the kitchen sink feature set" is
about.

This seems to be a popular meme, right until someone asks for details –
_crickets chirp_.

~~~
qammm
Well, with "Scala with its everything and the kitchen sink feature set" I mean
that Scala incorporates almost all language features one can think of for a
statically compiled programming language (I don't think it makes sense to
distinguish if a certain feature is provided by the language itself or a
library as in Scala that distinction is fuzzy): \- type inference \- classes
\- interfaces (sort of: traits) \- methods \- variables (var) \- immutable
values (val) \- higher order functions \- singletons \- functional
programming: map, flatMap, reduce/fold, ... \- actors \- coroutines (I think
there was a compiler plugin for that) \- implicits \- powerful type parameters
\- Futures \- it even has a turing complete type system

That is good and bad. Good: you can probably find good use for every feature
Scala has. Bad: On a sufficiently big project with one or more extra clever
developers most probably every feature will be used and that will make it
extra hard to understand for normal software developers that have to maintain
it for long years after the original extra smart developer already left the
company. See it a bit like that: On a hard to understand scale with 1 being
easy to understand und 10 being extremely hard to understand Java projects can
go from 1 to 6 and Scala projects can go from 1 to 10.

Personally I like simple languages more. And I don't need a compiler to catch
errors that a unit test would also catch.

~~~
happy_dino
I guess it depends on where one comes from. If one compares Scala to Scheme,
sure, Scheme is ridiculously simple compared to Scala.

But if one compares Scala to languages which are actually used in the wild
like Java, C#, PHP or C++; Scala's footprint is just incredibly small.

All of the features you mentioned are available in languages like Java or C#,
too. The difference is that in most cases the implementation is so poor and
incoherent, that the feature is next to useless.

I guess one just "sees" more language features being used in Scala, because
almost everything which ships in the language makes some sense, while in
Java/C#/PHP/C++ you have tons of utterly useless "features" which don't add
any benefit, but still force people to learn them in case somebody else used
them.

I have never seen "On a sufficiently big project with one or more extra clever
developers most probably every feature will be used" happen in real life. In
my experience one of the strengths of Scala is the way one can use some
advanced feature where it makes sense, without having it bleed through the
whole code. Compare that with Java's, C#'s "Oh, you used some complicated
Generic type over there? Guess what, we will make every user suffer from it
throughout your whole code base!"

In a sense, I prefer a language (Scala) which ships with 100 features where 90
of them make sense to a language which ships with 400 features where only 50
make sense, like C# (multiply "feature" count by 10 for C++).

    
    
      > And I don't need a compiler to catch errors that a unit test would also catch.
    

Well, using the compiler means that it will also catch errors which you
haven't written unit tests for. Tests can't prove the absence of certain
categories of errors, compilers can.

~~~
qammm
I don't want to sidetrack that thread as it was about Clojure. Just a quick
correction: Java has no type inference, higher order functions, coroutines,
implicits (it has some standard implicit conversions but not implicit
conversions that can be added by the user) and no Turing complete type system.

And of course: Using a statically typed language is no excuse to not write
unit tests. Unit tests serve as a safety net checking if the behavior of the
implemented unit is (and stays) correct. As a side effect this will also find
all type errors a compiler will find. I have programmed a lot in Java and also
in dynamic programming languages and in my opinion type errors just don't
happen often enough to justify the additional amount of work and complexity
that comes with static type systems. However I'd agree that if you want to get
the best possible performance you probably need a statically typed language as
the compiler can then optimize the generated code better.

~~~
happy_dino

      > Java has no type inference, higher order functions,
      > coroutines, implicits (it has some standard implicit
      > conversions but not implicit conversions that can be
      > added by the user) and no Turing complete type system.
    

Type inference in Java:

    
    
      int bar = new Object(){ int foo = 42; }.foo;
      // Magic? No. Type inference.
    

Higher order functions in Java:

    
    
      http://download.java.net/jdk8/docs/api/java/util/stream/Stream.html
      Looks pretty higher-order to me.
      Also possible in older version in Java with stuff like Google Guava or FJ.
    

Coroutines in Java:

    
    
      http://stackoverflow.com/questions/2846428/available-coroutine-libraries-in-java
    

Implicits:

    
    
      Having them built into the language is even worse.
      In Scala you could just de-import them and have them gone.
      Anyway, pick C# as an example instead if you want to have
      user-defined implicit conversions.
    

No Turing complete type system:

    
    
      interface Interface<T> {}
      class Bang<T> implements Interface<Interface<? super Bang<Bang<T>>>> {
          static void bang() {
              Interface<? super Bang<Byte>> bang = new Bang<Byte>();
          }
      }
    
      Looks pretty undecidable to me. In a way, it is even
      worse than other languages: You are unable to tell
      whether the type checker will terminate in finite time
      (like some other languages), but don't get any additional
      expressivness in return (unlike those other languages).
    
    
      > As a side effect this will also find all type errors
      > a compiler will find.
    

No, absolutely not.

    
    
      > I have programmed a lot in Java and also in dynamic
      > programming languages and in my opinion type errors
      > just don't happen often enough to justify the
      > additional amount of work and complexity that comes
      > with static type systems.
    

This comment certainly explains a lot. You are suffering from the "I used Java
and Java is statically typed and it sucks, therefore all statically typed
languages have to suck" fallacy.

~~~
qammm
It seems we have different definitions of what type inference, higher order
functions and Turing completeness means. :-) Regarding coroutines in Java: I
don't know if libraries using native continuation mechanisms or bytecode
manipulations prove that Java (the language) has continuation support. :-) I
don't have anything against Scala. In my very first message I even said that I
see the odds for Scala winning higher than the odds for Clojure winning -
because I already see some enterprise adoption of Scala. Although I see the
probability of Scala winning quite low. As you noticed with Java 8 Java is
already borrowing a lot of useful things from Scala. I am sure conservative
corporate decision makers will see less and less reasons to switch to Scala as
time passes by. Also I don't think that Java sucks. I was just making a point
from personal productivity experience. Your experience might differ from that.

If I have a function: def upcase(s: String): String... The compiler with its
static type system can tell me if e. g. I am trying to call the upcase
function with an Int argument. But in my experience something like that just
does not happen very often. Most programmers are not so stupid that they try
to fit a square peg in a round hole. ;-)

A unit test can check if the returned string is really the upcase version of
the input parameter. Plus if the programmer would really assume that he could
upcase an Int it would just as well give the feedback that his assumption was
wrong-like the compiler.

~~~
happy_dino

      > It seems we have different definitions of what type 
      > inference, higher order functions and Turing 
      > completeness means. :-)
    

I don't think so. The definitions are pretty much standard and those are the
ones I'm using.

I think we can agree that the way Java supports those features ranges between
unusable and pretty terrible in practice, but that's not what your claims were
about.

Your notion of Scala having more features than a "standard" mainstream
language might even be correct, it is just that the points you have given
don't support your point here.

    
    
      > Regarding coroutines in Java: I don't know if libraries
      > using native continuation mechanisms or bytecode
      > manipulations prove that Java (the language) has
      > continuation support. :-)
    

Then Scala doesn't have continuation support either. Whatever definition is
applied, it needs to be applied consistently.

    
    
      > I don't have anything against Scala.
    

I never suggested that and even if you had something against Scala, it would
be perfectly fine – for me and probably for everyone else.

It's just that you have claimed a few things which I think are incorrect,
either factually or in the way they were worded, and I'm offering some data
points against it. This all happens in good faith and in the hope that we both
will have gained some knowledge at the end of this discussion.

    
    
      > As you noticed with Java 8 Java is already borrowing a lot
      > of useful things from Scala. I am sure conservative
      > corporate decision makers will see less and less reasons
      > to switch to Scala as time passes by.
    

I think most Scala users would agree that Java 8 copying Scala is a good
thing, because it strongly validates what the designers and users of Scala
have been doing for the last 10 years. With Java moving closer to Scala,
adopting Scala becomes a lot easier from a management POV which in turn
removes a lot of the concerns corporate decision makers have.

    
    
      > If I have a function: def upcase(s: String): String [...]
      > A unit test can check if the returned string is really
      > the upcase version of the input parameter.
    
      def upcase(s: String): UppercasedString
    

Now the compiler can check it, too.

~~~
qammm
Only replying partially as I don't want to repeat myself.

Ok, then let's just ignore continuations as they are somehow available in both
languages although the Scala one feels a bit more officially endorsed to me.

> def upcase(s: String): UppercasedString

Even with that type signature of course the compiler can not check that for
input "a" the output will be "A". Your code could have a bug and upcase "a" to
"B" (Off-by-one errors are quite common) and your compiler would be perfectly
happy. That is the whole point why unit test are more valuable than compiler
type checks: checking specific code behavior and not only static types.

------
dustingetz
michaelochurch's closing sentence: _" Unlike the typical enterprise Java
stack, it’s optimized for lifelong learners. That, above all, is why it will
win."_

Here's a speculative reason why it may not win:

Java, Ruby, PHP, Python all won because intermediate level programmers could,
all of a sudden, successfully build 2000-era sized apps.

These languages are not doing so hot for 2013-era sized apps. It now takes
extreme skills to successfully ship 2013-sized apps which is why a small
portion of the programmers are making most of the money.

The next language to win will be the one that lets an intermediate team ship
apps again. Java let your average C++ programmer build much bigger apps
without crashing. In 2000, Java _forced_ you to program right by 2000
standards; the programmer needn't have figured it out himself.

A language that lets a strong architect say, "NO! you CANNOT do I/O in the
view, that goes in the controller!", that lets an architect shape what good
code should look like and have the language enforce it, can lead a team of
intermediate programmers to success.

Clojure is like a musical instrument - a brilliant artist can do amazing
things, but a mediocre artist will produce mediocre output. Clojure works
great if you have 5 brilliant architects collaborating - Datomic, core.async,
ClojureScript, all these are outputs of brilliant minds collaborating; the
company behind these products has a reputation for only hiring the best of the
best.

But I think a business can make more money by putting 5 brilliant architects
on 5 separate projects and giving them a bunch of intermediate programmers.
The intermediate programmers learn; the architect multiplies; the pointy
haired boss gets rich, everybody wins.

------
sultezdukes
I never did see his definition of "win", but Clojure does have a great
community and I consider that one of its greatest strengths.

That said, I can never see Clojure "winning" as in how Java "won". For all of
Clojure's strengths, it's at best an intermediate step up from Ruby, Python,
Perl... It's not that next order of magnitude leap of productivity that is
necessary to "win".

The research just isn't going in that direction. The research is going into
type systems and static guarantees. And I think the real productivity boosters
of the future will be in very smart tooling - a conversation with your IDE I
would say. Maybe Clojure could have different views (different surface
syntaxes). Maybe it could be the basis of something like intentional
programming. But straight Clojure with Emacs isn't going to be "winning" in
the big way.

------
happy_dino

      > but it will win in the next 15 years in a major way, 
      > because it is already one of the most interesting
    

the most interesting ... what?

Anyway, I think they have already won in a major way: The managed to build a
community which is supportive and friendly. This is a huge deal when you have
a look at the poisonous behaviours of individuals and the wide-spread
arrogance typical in most Lisp communities.

Before I learned about Clojure, I certainly wouldn't have believed it if
someone told me that there was a Lisp-like language without the pretentious
assholes.

    
    
      > An enterprise Scala project, for example, is typically 
      > going to present the frustrations that come with 
      > components that live outside the language. Learning Scala 
      > isn’t that bad, but Maven and Spring and Hibernate? Ouch. 
      > In Clojure, most of the typically “external” needs are 
      > provided with idiomatic libraries that can be reasoned 
      > about within the language.
    

That doesn't make much sense. One can do exactly the same in Scala. The big
improvement on Clojure is that it is completely pain-free and seamless to keep
the old components around and migrate gradually to better solutions (or just
keep the legacy parts which work – why bother changing it?).

    
    
      > while every static language worth its salt has an 
      > interactive mode (“REPL”) it doesn’t have the same
      > first-class-citizen feel
    

Maybe this has changed, but the last time I used Clojure's REPL, it was
completely unusable, with basic things like auto-completion, history and
navigation being completely non-functional.

I think the opinion voiced in the article is interesting, but past experience
tells us that the chances of a Lisp to get even slightly popular is low to
non-existing.

~~~
gruseom
_the poisonous behaviours of individuals and the wide-spread arrogance typical
in most Lisp communities_

Is that really true of most Lisp communities, or just Common Lisp's?

~~~
lispm
It must be true for others, too. happy_dino is a good example.

